static void
ft_transfer_operation_callback (EmpathyTpFile *tp_file,
    const GError *error,
    gpointer user_data)
{
  EmpathyFTHandler *handler = user_data;
  EmpathyFTHandlerPriv *priv = GET_PRIV (handler);

  DEBUG ("Transfer operation callback, error %p", error);

  if (error != NULL)
    {
      emit_error_signal (handler, error);
    }
  else
    {
      priv->is_completed = TRUE;
      g_signal_emit (handler, signals[TRANSFER_DONE], 0, tp_file);

      empathy_tp_file_close (tp_file);

      if (empathy_ft_handler_is_incoming (handler) && priv->use_hash)
        {
          check_hash_incoming (handler);
        }
    }
}
Beispiel #2
0
static void
ft_handler_hashing_started_cb (EmpathyFTHandler *handler,
                               EmpathyFTManager *manager)
{
  char *message, *first_line, *second_line;
  GtkTreeRowReference *row_ref;

  DEBUG ("Hashing started");

  g_signal_connect (handler, "hashing-progress",
     G_CALLBACK (ft_handler_hashing_progress_cb), manager);
  g_signal_connect (handler, "hashing-done",
     G_CALLBACK (ft_handler_hashing_done_cb), manager);

  row_ref = ft_manager_get_row_from_handler (manager, handler);
  g_return_if_fail (row_ref != NULL);

  first_line = ft_manager_format_contact_info (handler);

  if (empathy_ft_handler_is_incoming (handler))
      second_line = g_strdup_printf (_("Checking integrity of “%s”"),
          empathy_ft_handler_get_filename (handler));
  else
      second_line = g_strdup_printf (_("Hashing “%s”"),
          empathy_ft_handler_get_filename (handler));

  message = g_strdup_printf ("%s\n%s", first_line, second_line);

  ft_manager_update_handler_message (manager, row_ref, message);

  g_free (first_line);
  g_free (second_line);
  g_free (message);
}
Beispiel #3
0
static void
ft_manager_start_transfer (EmpathyFTManager *manager,
                           EmpathyFTHandler *handler)
{
  gboolean is_outgoing;

  is_outgoing = !empathy_ft_handler_is_incoming (handler);

  DEBUG ("Start transfer, is outgoing %s",
      is_outgoing ? "True" : "False");

  /* now connect the signals */
  g_signal_connect (handler, "transfer-error",
      G_CALLBACK (ft_handler_transfer_error_cb), manager);

  if (is_outgoing && empathy_ft_handler_get_use_hash (handler)) {
    g_signal_connect (handler, "hashing-started",
        G_CALLBACK (ft_handler_hashing_started_cb), manager);
  } else {
    /* either incoming or outgoing without hash */
    g_signal_connect (handler, "transfer-started",
        G_CALLBACK (ft_handler_transfer_started_cb), manager);
  }

  empathy_ft_handler_start_transfer (handler);
}
Beispiel #4
0
static void
ft_handler_hashing_done_cb (EmpathyFTHandler *handler,
                            EmpathyFTManager *manager)
{
  GtkTreeRowReference *row_ref;
  char *first_line, *second_line, *message;

  DEBUG ("Hashing done");

  /* update the message */
  if (empathy_ft_handler_is_incoming (handler))
    {
      do_real_transfer_done (manager, handler);
      return;
    }

  row_ref = ft_manager_get_row_from_handler (manager, handler);
  g_return_if_fail (row_ref != NULL);

  first_line = ft_manager_format_contact_info (handler);
  second_line = g_strdup (_("Waiting for the other participant’s response"));
  message = g_strdup_printf ("%s\n%s", first_line, second_line);

  ft_manager_update_handler_message (manager, row_ref, message);

  g_free (message);
  g_free (first_line);
  g_free (second_line);

  g_signal_connect (handler, "transfer-started",
      G_CALLBACK (ft_handler_transfer_started_cb), manager);
}
Beispiel #5
0
static void
ft_handler_hashing_progress_cb (EmpathyFTHandler *handler,
                                guint64 current_bytes,
                                guint64 total_bytes,
                                EmpathyFTManager *manager)
{
  char *first_line, *second_line, *message;
  GtkTreeRowReference *row_ref;

  row_ref = ft_manager_get_row_from_handler (manager, handler);
  g_return_if_fail (row_ref != NULL);

  if (empathy_ft_handler_is_incoming (handler))
      first_line = g_strdup_printf (_("Checking integrity of “%s”"),
          empathy_ft_handler_get_filename (handler));
  else
      first_line =  g_strdup_printf (_("Hashing “%s”"),
          empathy_ft_handler_get_filename (handler));

  second_line = ft_manager_format_progress_bytes_and_percentage
    (current_bytes, total_bytes, -1, NULL);

  message = g_strdup_printf ("%s\n%s", first_line, second_line);

  ft_manager_update_handler_message (manager, row_ref, message);

  g_free (message);
  g_free (first_line);
  g_free (second_line);
}
Beispiel #6
0
static void
ft_transfer_state_cb (TpFileTransferChannel *channel,
    GParamSpec *pspec,
    EmpathyFTHandler *handler)
{
  EmpathyFTHandlerPriv *priv = handler->priv;
  TpFileTransferStateChangeReason reason;
  TpFileTransferState state = tp_file_transfer_channel_get_state (
      channel, &reason);

  (void)pspec;      /* suppress unused-parameter warning */

  if (state == TP_FILE_TRANSFER_STATE_COMPLETED)
    {
      priv->is_completed = TRUE;
      g_signal_emit (handler, signals[TRANSFER_DONE], 0, channel);

      tp_channel_close_async (TP_CHANNEL (channel), NULL, NULL);

      if (empathy_ft_handler_is_incoming (handler) && priv->use_hash)
        {
          check_hash_incoming (handler);
        }
    }
  else if (state == TP_FILE_TRANSFER_STATE_CANCELLED)
    {
      GError *error = error_from_state_change_reason (reason);
      emit_error_signal (handler, error);
      g_clear_error (&error);
    }
}
Beispiel #7
0
static void
do_real_transfer_done (EmpathyFTManager *manager,
                       EmpathyFTHandler *handler)
{
  const char *contact_name;
  const char *filename;
  char *first_line, *second_line, *message;
  char *uri;
  gboolean incoming;
  GtkTreeRowReference *row_ref;
  GtkRecentManager *recent_manager;
  GFile *file;

  row_ref = ft_manager_get_row_from_handler (manager, handler);
  g_return_if_fail (row_ref != NULL);

  incoming = empathy_ft_handler_is_incoming (handler);
  contact_name = empathy_contact_get_alias
    (empathy_ft_handler_get_contact (handler));
  filename = empathy_ft_handler_get_filename (handler);

  if (incoming)
    /* translators: first %s is filename, second %s
     * is the contact name */
    first_line = g_strdup_printf (_("“%s” received from %s"), filename,
        contact_name);
  else
    /* translators: first %s is filename, second %s
     * is the contact name */
    first_line = g_strdup_printf (_("“%s” sent to %s"), filename,
        contact_name);

  second_line = g_strdup (_("File transfer completed"));

  message = g_strdup_printf ("%s\n%s", first_line, second_line);
  ft_manager_update_handler_message (manager, row_ref, message);
  ft_manager_clear_handler_time (manager, row_ref);

  /* update buttons */
  ft_manager_update_buttons (manager);

  g_free (message);
  g_free (first_line);
  g_free (second_line);

  recent_manager = gtk_recent_manager_get_default ();
  file = empathy_ft_handler_get_gfile (handler);
  uri = g_file_get_uri (file);

  gtk_recent_manager_add_item (recent_manager, uri);

  g_free (uri);
}
Beispiel #8
0
static void
ft_manager_update_buttons (EmpathyFTManager *manager)
{
  GtkTreeSelection *selection;
  GtkTreeModel *model;
  GtkTreeIter iter;
  EmpathyFTHandler *handler;
  gboolean open_enabled = FALSE;
  gboolean abort_enabled = FALSE;
  gboolean clear_enabled = FALSE;
  gboolean is_completed, is_cancelled;
  GHashTableIter hash_iter;
  EmpathyFTManagerPriv *priv = GET_PRIV (manager);

  selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->treeview));

  if (gtk_tree_selection_get_selected (selection, &model, &iter))
    {
      gtk_tree_model_get (model, &iter, COL_FT_OBJECT, &handler, -1);

      is_completed = empathy_ft_handler_is_completed (handler);
      is_cancelled = empathy_ft_handler_is_cancelled (handler);

      /* I can open the file if the transfer is completed and was incoming */
      open_enabled = (is_completed && empathy_ft_handler_is_incoming (handler));

      /* I can abort if the transfer is not already finished */
      abort_enabled = (is_cancelled == FALSE && is_completed == FALSE);

      g_object_unref (handler);
    }

  g_hash_table_iter_init (&hash_iter, priv->ft_handler_to_row_ref);

  while (g_hash_table_iter_next (&hash_iter, (gpointer *) &handler, NULL))
    {
      if (empathy_ft_handler_is_completed (handler) ||
          empathy_ft_handler_is_cancelled (handler))
          clear_enabled = TRUE;

      if (clear_enabled)
        break;
    }

  gtk_widget_set_sensitive (priv->open_button, open_enabled);
  gtk_widget_set_sensitive (priv->abort_button, abort_enabled);

  if (clear_enabled)
    gtk_widget_set_sensitive (priv->clear_button, TRUE);
}
Beispiel #9
0
static gchar *
ft_manager_format_error_message (EmpathyFTHandler *handler,
                                 const GError *error)
{
  const char *contact_name, *filename;
  EmpathyContact *contact;
  char *first_line, *message;
  gboolean incoming;

  contact_name = NULL;
  incoming = empathy_ft_handler_is_incoming (handler);

  contact = empathy_ft_handler_get_contact (handler);
  if (contact)
    contact_name = empathy_contact_get_alias (contact);

  filename = empathy_ft_handler_get_filename (handler);

  if (incoming)
    /* filename/contact_name here are either both NULL or both valid */
    if (filename && contact_name)
      /* translators: first %s is filename, second %s
       * is the contact name */
      first_line = g_strdup_printf (_("Error receiving “%s” from %s"), filename,
          contact_name);
    else
      first_line = g_strdup (_("Error receiving a file"));
  else
    /* translators: first %s is filename, second %s
     * is the contact name */
    if (filename && contact_name)
      first_line = g_strdup_printf (_("Error sending “%s” to %s"), filename,
          contact_name);
    else
      first_line = g_strdup (_("Error sending a file"));

  message = g_strdup_printf ("%s\n%s", first_line, error->message);

  g_free (first_line);

  return message;
}
Beispiel #10
0
static void
ft_handler_transfer_done_cb (EmpathyFTHandler *handler,
                             TpFileTransferChannel *channel,
                             EmpathyFTManager *manager)
{
  if (empathy_ft_handler_is_incoming (handler) &&
      empathy_ft_handler_get_use_hash (handler))
    {
      DEBUG ("Transfer done, waiting for hashing-started");

      /* connect to the signal and return early */
      g_signal_connect (handler, "hashing-started",
          G_CALLBACK (ft_handler_hashing_started_cb), manager);

      return;
    }

  DEBUG ("Transfer done, no hashing");

  do_real_transfer_done (manager, handler);
}
Beispiel #11
0
static gchar *
ft_manager_format_contact_info (EmpathyFTHandler *handler)
{
  gboolean incoming;
  const char *filename, *contact_name, *first_line_format;
  char *retval;

  incoming = empathy_ft_handler_is_incoming (handler);
  contact_name = empathy_contact_get_alias
    (empathy_ft_handler_get_contact (handler));
  filename = empathy_ft_handler_get_filename (handler);

  if (incoming)
    /* translators: first %s is filename, second %s is the contact name */
    first_line_format = _("Receiving “%s” from %s");
  else
    /* translators: first %s is filename, second %s is the contact name */
    first_line_format = _("Sending “%s” to %s");

  retval = g_strdup_printf (first_line_format, filename, contact_name);

  return retval;
}
static gboolean
hash_job_done (gpointer user_data)
{
  HashingData *hash_data = user_data;
  EmpathyFTHandler *handler = hash_data->handler;
  EmpathyFTHandlerPriv *priv;
  GError *error = NULL;

  DEBUG ("Closing stream after hashing.");

  priv = GET_PRIV (handler);

  if (hash_data->error != NULL)
    {
      error = hash_data->error;
      hash_data->error = NULL;
      goto cleanup;
    }

  DEBUG ("Got file hash %s", g_checksum_get_string (hash_data->checksum));

  if (empathy_ft_handler_is_incoming (handler))
    {
      if (g_strcmp0 (g_checksum_get_string (hash_data->checksum),
                     priv->content_hash))
        {
          DEBUG ("Hash mismatch when checking incoming handler: "
                 "received %s, calculated %s", priv->content_hash,
                 g_checksum_get_string (hash_data->checksum));

          error = g_error_new_literal (EMPATHY_FT_ERROR_QUARK,
              EMPATHY_FT_ERROR_HASH_MISMATCH,
              _("File transfer completed, but the file was corrupted"));
          goto cleanup;
        }
      else
        {
          DEBUG ("Hash verification matched, received %s, calculated %s",
                 priv->content_hash,
                 g_checksum_get_string (hash_data->checksum));
        }
    }
  else
    {
      /* set the checksum in the request...
       * org.freedesktop.Telepathy.Channel.Type.FileTransfer.ContentHash
       */
      tp_asv_set_string (priv->request,
          TP_PROP_CHANNEL_TYPE_FILE_TRANSFER_CONTENT_HASH,
          g_checksum_get_string (hash_data->checksum));
    }

cleanup:

  if (error != NULL)
    {
      emit_error_signal (handler, error);
      g_clear_error (&error);
    }
  else
    {
      g_signal_emit (handler, signals[HASHING_DONE], 0);

      if (!empathy_ft_handler_is_incoming (handler))
        /* the request is complete now, push it to the dispatcher */
        ft_handler_push_to_dispatcher (handler);
    }

  hash_data_free (hash_data);

  return FALSE;
}
Beispiel #13
0
static void
ft_manager_add_handler_to_list (EmpathyFTManager *manager,
                                EmpathyFTHandler *handler,
                                const GError *error)
{
  GtkTreeRowReference *row_ref;
  GtkTreeIter iter;
  GtkTreeSelection *selection;
  GtkTreePath *path;
  GIcon *icon;
  const char *content_type, *second_line;
  char *first_line, *message;
  EmpathyFTManagerPriv *priv = GET_PRIV (manager);

  icon = NULL;

  /* get the icon name from the mime-type of the file. */
  content_type = empathy_ft_handler_get_content_type (handler);

  if (content_type != NULL)
    icon = g_content_type_get_icon (content_type);

  /* append the handler in the store */
  gtk_list_store_insert_with_values (GTK_LIST_STORE (priv->model),
      &iter, G_MAXINT, COL_FT_OBJECT, handler,
      COL_ICON, icon, -1);

  if (icon != NULL)
    g_object_unref (icon);

  /* insert the new row_ref in the hash table  */
  path = gtk_tree_model_get_path (GTK_TREE_MODEL (priv->model), &iter);
  row_ref = gtk_tree_row_reference_new (GTK_TREE_MODEL (priv->model), path);
  gtk_tree_path_free (path);
  g_hash_table_insert (priv->ft_handler_to_row_ref, g_object_ref (handler),
      row_ref);

  /* select the new row */
  selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->treeview));
  gtk_tree_selection_select_iter (selection, &iter);

  if (error != NULL)
    {
      message = ft_manager_format_error_message (handler, error);
      ft_manager_update_handler_message (manager, row_ref, message);

      g_free (message);
      return;
    }

  /* update the row with the initial values.
   * the only case where we postpone this is in case we're managing
   * an outgoing+hashing transfer, as the hashing started signal will
   * take care of updating the information.
   */
  if (empathy_ft_handler_is_incoming (handler) ||
      !empathy_ft_handler_get_use_hash (handler)) {
    first_line = ft_manager_format_contact_info (handler);
    second_line = _("Waiting for the other participant’s response");
    message = g_strdup_printf ("%s\n%s", first_line, second_line);

    ft_manager_update_handler_message (manager, row_ref, message);

    g_free (first_line);
    g_free (message);
  }

  /* hook up the signals and start the transfer */
  ft_manager_start_transfer (manager, handler);
}