static void
ft_transfer_progress_callback (EmpathyTpFile *tp_file,
    guint64 transferred_bytes,
    gpointer user_data)
{
  EmpathyFTHandler *handler = user_data;
  EmpathyFTHandlerPriv *priv = GET_PRIV (handler);

  if (empathy_ft_handler_is_cancelled (handler))
    return;

  if (transferred_bytes == 0)
    {
      priv->last_update_time = empathy_time_get_current ();
      g_signal_emit (handler, signals[TRANSFER_STARTED], 0, tp_file);
    }

  if (priv->transferred_bytes != transferred_bytes)
    {
      update_remaining_time_and_speed (handler, transferred_bytes);

      g_signal_emit (handler, signals[TRANSFER_PROGRESS], 0,
          transferred_bytes, priv->total_bytes, priv->remaining_time,
          priv->speed);
    }
}
static void
update_remaining_time_and_speed (EmpathyFTHandler *handler,
    guint64 transferred_bytes)
{
  EmpathyFTHandlerPriv *priv = GET_PRIV (handler);
  gint64 elapsed_time, current_time;
  guint64 transferred, last_transferred_bytes;
  gdouble speed;
  gint remaining_time;

  last_transferred_bytes = priv->transferred_bytes;
  priv->transferred_bytes = transferred_bytes;

  current_time = empathy_time_get_current ();
  elapsed_time = current_time - priv->last_update_time;

  if (elapsed_time >= 1)
    {
      transferred = transferred_bytes - last_transferred_bytes;
      speed = (gdouble) transferred / (gdouble) elapsed_time;
      remaining_time = (priv->total_bytes - priv->transferred_bytes) / speed;
      priv->speed = speed;
      priv->remaining_time = remaining_time;
      priv->last_update_time = current_time;
    }
}
Example #3
0
static gchar *
log_manager_get_timestamp_filename (void)
{
	time_t      t;
	gchar      *time_str;
	gchar      *filename;

	t = empathy_time_get_current ();
	time_str = empathy_time_to_string_local (t, LOG_TIME_FORMAT);
	filename = g_strconcat (time_str, LOG_FILENAME_SUFFIX, NULL);

	g_free (time_str);

	return filename;
}
static void
chat_text_view_append_event (EmpathyChatView *view,
			     const gchar     *str)
{
	EmpathyChatTextView     *text_view = EMPATHY_CHAT_TEXT_VIEW (view);
	EmpathyChatTextViewPriv *priv = GET_PRIV (text_view);
	gboolean                 bottom;
	GtkTextIter              iter;
	gchar                   *msg;


	g_return_if_fail (EMPATHY_IS_CHAT_TEXT_VIEW (view));
	g_return_if_fail (!EMP_STR_EMPTY (str));

	bottom = chat_text_view_is_scrolled_down (text_view);
	chat_text_view_maybe_trim_buffer (EMPATHY_CHAT_TEXT_VIEW (view));
	chat_text_maybe_append_date_and_time (text_view,
					      empathy_time_get_current ());

	gtk_text_buffer_get_end_iter (priv->buffer, &iter);
	msg = g_strdup_printf (" - %s\n", str);
	gtk_text_buffer_insert_with_tags_by_name (priv->buffer, &iter,
						  msg, -1,
						  EMPATHY_CHAT_TEXT_VIEW_TAG_EVENT,
						  NULL);
	g_free (msg);

	if (bottom) {
		chat_text_view_scroll_down (view);
	}
	
	if (priv->last_contact) {
		g_object_unref (priv->last_contact);
		priv->last_contact = NULL;
		g_object_notify (G_OBJECT (view), "last-contact");
	}
}
static void
tp_file_start_transfer (EmpathyTpFile *self)
{
  gint fd, domain, res = 0;
  GError *error = NULL;
  struct sockaddr *my_addr = NULL;
  size_t my_size = 0;

  if (self->priv->socket_address_type == TP_SOCKET_ADDRESS_TYPE_UNIX)
    {
      domain = AF_UNIX;
    }
  else if (self->priv->socket_address_type == TP_SOCKET_ADDRESS_TYPE_IPV4)
    {
      domain = AF_INET;
    }
  else
    {
      error = g_error_new_literal (EMPATHY_FT_ERROR_QUARK,
          EMPATHY_FT_ERROR_NOT_SUPPORTED, _("Socket type not supported"));

      DEBUG ("Socket not supported, closing channel");

      ft_operation_close_with_error (self, error);
      g_clear_error (&error);

      return;
    }

  fd = socket (domain, SOCK_STREAM, 0);

  if (fd < 0)
    {
      int code = errno;

      error = g_error_new_literal (EMPATHY_FT_ERROR_QUARK,
          EMPATHY_FT_ERROR_SOCKET, g_strerror (code));

      DEBUG ("Failed to create socket, closing channel");

      ft_operation_close_with_error (self, error);
      g_clear_error (&error);

      return;
    }

  if (self->priv->socket_address_type == TP_SOCKET_ADDRESS_TYPE_UNIX)
    {
      struct sockaddr_un addr;

      memset (&addr, 0, sizeof (addr));
      addr.sun_family = domain;
      strncpy (addr.sun_path, self->priv->socket_address->data,
          self->priv->socket_address->len);

      my_addr = (struct sockaddr *) &addr;
      my_size = sizeof (addr);
    }
  else if (self->priv->socket_address_type == TP_SOCKET_ADDRESS_TYPE_IPV4)
    {
      struct sockaddr_in addr;

      memset (&addr, 0, sizeof (addr));
      addr.sin_family = domain;
      inet_pton (AF_INET, self->priv->socket_address->data, &addr.sin_addr);
      addr.sin_port = htons (self->priv->port);

      my_addr = (struct sockaddr *) &addr;
      my_size = sizeof (addr);
    }

  res = connect (fd, my_addr, my_size);

  if (res < 0)
    {
      int code = errno;

      error = g_error_new_literal (EMPATHY_FT_ERROR_QUARK,
          EMPATHY_FT_ERROR_SOCKET, g_strerror (code));

      DEBUG ("Failed to connect socket, closing channel");

      ft_operation_close_with_error (self, error);
      close (fd);
      g_clear_error (&error);

      return;
    }

  DEBUG ("Start the transfer");

  self->priv->start_time = empathy_time_get_current ();

  /* notify we're starting a transfer */
  if (self->priv->progress_callback != NULL)
    self->priv->progress_callback (self, 0, self->priv->progress_user_data);

  if (self->priv->incoming)
    {
      GInputStream *socket_stream;

      socket_stream = g_unix_input_stream_new (fd, TRUE);

      g_output_stream_splice_async (self->priv->out_stream, socket_stream,
          G_OUTPUT_STREAM_SPLICE_CLOSE_SOURCE |
          G_OUTPUT_STREAM_SPLICE_CLOSE_TARGET,
          G_PRIORITY_DEFAULT, self->priv->cancellable,
          splice_stream_ready_cb, self);

      g_object_unref (socket_stream);
    }
  else
    {
      GOutputStream *socket_stream;

      socket_stream = g_unix_output_stream_new (fd, TRUE);

      g_output_stream_splice_async (socket_stream, self->priv->in_stream,
          G_OUTPUT_STREAM_SPLICE_CLOSE_SOURCE |
          G_OUTPUT_STREAM_SPLICE_CLOSE_TARGET,
          G_PRIORITY_DEFAULT, self->priv->cancellable,
          splice_stream_ready_cb, self);

      g_object_unref (socket_stream);
    }
}