gnome-session r4633 - in branches/gnome-2-22: . gnome-session
- From: vuntz svn gnome org
- To: svn-commits-list gnome org
- Subject: gnome-session r4633 - in branches/gnome-2-22: . gnome-session
- Date: Mon, 7 Apr 2008 23:43:54 +0100 (BST)
Author: vuntz
Date: Mon Apr 7 23:43:54 2008
New Revision: 4633
URL: http://svn.gnome.org/viewvc/gnome-session?rev=4633&view=rev
Log:
2008-04-08 Vincent Untz <vuntz gnome org>
Add code to migrate the Trash to the new location.
Temporary fix for bug #517561, until we get a proper infrastructure.
* gnome-session/Makefile.am: add new files
* gnome-session/main.c: (main): call migrate_trash()
* gnome-session/migrate-trash.[ch]: new
Added:
branches/gnome-2-22/gnome-session/migrate-trash.c
branches/gnome-2-22/gnome-session/migrate-trash.h
Modified:
branches/gnome-2-22/ChangeLog
branches/gnome-2-22/gnome-session/Makefile.am
branches/gnome-2-22/gnome-session/main.c
Modified: branches/gnome-2-22/gnome-session/Makefile.am
==============================================================================
--- branches/gnome-2-22/gnome-session/Makefile.am (original)
+++ branches/gnome-2-22/gnome-session/Makefile.am Mon Apr 7 23:43:54 2008
@@ -103,7 +103,9 @@
gsm-keyfile.h \
headers.h \
util.c \
- util.h
+ util.h \
+ migrate-trash.c \
+ migrate-trash.h
gnome_session_save_SOURCES = \
gnome-session-save.c \
Modified: branches/gnome-2-22/gnome-session/main.c
==============================================================================
--- branches/gnome-2-22/gnome-session/main.c (original)
+++ branches/gnome-2-22/gnome-session/main.c Mon Apr 7 23:43:54 2008
@@ -53,6 +53,7 @@
#include "gsm-keyring.h"
#include "gsm-at-startup.h"
#include "gsm-remote-desktop.h"
+#include "migrate-trash.h"
/* Flag indicating autosave - user won't be prompted on logout to
* save the session */
@@ -783,6 +784,8 @@
start_session (the_session);
+ migrate_trash();
+
gtk_main ();
gsm_remote_desktop_cleanup ();
Added: branches/gnome-2-22/gnome-session/migrate-trash.c
==============================================================================
--- (empty file)
+++ branches/gnome-2-22/gnome-session/migrate-trash.c Mon Apr 7 23:43:54 2008
@@ -0,0 +1,314 @@
+/* Compile with:
+ * gcc -o migrate-trash `pkg-config --cflags --libs glib-2.0` migrate-trash.c
+ */
+
+/* Migrate code from ~/.Trash (GNOME < 2.22) to the new trash fd.o spec
+ *
+ * Copyright (C) 2008 Novell, Inc.
+ * Author: Vincent Untz <vuntz gnome org>
+ *
+ * Some code is based on glocalfile.c (from glib/gio), with this
+ * copyright/license header:
+ *
+ * Copyright (C) 2006-2007 Red Hat, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General
+ * Public License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Author: Alexander Larsson <alexl redhat com>
+ */
+
+#include <errno.h>
+#include <fcntl.h>
+#include <string.h>
+
+#include <glib.h>
+#include <glib/gstdio.h>
+
+#include "migrate-trash.h"
+
+#define OLD_TRASH_DIR ".Trash"
+
+static gboolean
+create_new_trash (char **info_dir,
+ char **files_dir)
+{
+ char *trashdir;
+ char *infodir;
+ char *filesdir;
+
+ g_assert (info_dir && files_dir);
+
+ trashdir = g_build_filename (g_get_user_data_dir (), "Trash", NULL);
+ if (g_mkdir_with_parents (trashdir, 0700) < 0)
+ {
+ char *display_name;
+
+ display_name = g_filename_display_name (trashdir);
+ g_free (trashdir);
+
+ g_printerr ("Unable to create trash dir %s: %s\n", display_name,
+ g_strerror (errno));
+ g_free (display_name);
+
+ return FALSE;
+ }
+
+ /* Trashdir points to the trash dir with the "info" and "files"
+ * subdirectories */
+
+ infodir = g_build_filename (trashdir, "info", NULL);
+ filesdir = g_build_filename (trashdir, "files", NULL);
+ g_free (trashdir);
+
+ /* Make sure we have the subdirectories */
+ if ((g_mkdir (infodir, 0700) == -1 && errno != EEXIST) ||
+ (g_mkdir (filesdir, 0700) == -1 && errno != EEXIST))
+ {
+ g_free (infodir);
+ g_free (filesdir);
+
+ g_printerr ("Unable to find or create trash directory\n");
+ return FALSE;
+ }
+
+ *info_dir = infodir;
+ *files_dir = filesdir;
+
+ return TRUE;
+}
+
+static char *
+get_unique_filename (const char *basename,
+ int id)
+{
+ const char *dot;
+
+ if (id == 1)
+ return g_strdup (basename);
+
+ dot = strchr (basename, '.');
+ if (dot)
+ return g_strdup_printf ("%.*s.%d%s", (int)(dot - basename), basename, id, dot);
+ else
+ return g_strdup_printf ("%s.%d", basename, id);
+}
+
+static char *
+escape_trash_name (char *name)
+{
+ GString *str;
+ const gchar hex[16] = "0123456789ABCDEF";
+
+ str = g_string_new ("");
+
+ while (*name != 0)
+ {
+ char c;
+
+ c = *name++;
+
+ if (g_ascii_isprint (c))
+ g_string_append_c (str, c);
+ else
+ {
+ g_string_append_c (str, '%');
+ g_string_append_c (str, hex[((guchar)c) >> 4]);
+ g_string_append_c (str, hex[((guchar)c) & 0xf]);
+ }
+ }
+
+ return g_string_free (str, FALSE);
+}
+
+
+static gboolean
+move_file (const char *old_trash_dir,
+ const char *basename,
+ const char *infodir,
+ const char *filesdir)
+{
+ int i;
+ char *filename;
+ char *trashname;
+ char *infofile;
+ char *trashfile;
+ char *original_name;
+ char *original_name_escaped;
+ char delete_time[32];
+ char *data;
+ int fd;
+
+ i = 1;
+ trashname = NULL;
+ infofile = NULL;
+ do {
+ char *infoname;
+
+ g_free (trashname);
+ g_free (infofile);
+
+ trashname = get_unique_filename (basename, i++);
+ infoname = g_strconcat (trashname, ".trashinfo", NULL);
+ infofile = g_build_filename (infodir, infoname, NULL);
+ g_free (infoname);
+
+ fd = open (infofile, O_CREAT | O_EXCL, 0666);
+ } while (fd == -1 && errno == EEXIST);
+
+ if (fd == -1)
+ {
+ char *display_name;
+
+ g_free (trashname);
+ g_free (infofile);
+
+ display_name = g_filename_display_name (basename);
+
+ g_printerr (("Unable to create trashing info file for %s: %s\n"),
+ display_name, g_strerror (errno));
+
+ g_free (display_name);
+
+ return FALSE;
+ }
+
+ close (fd);
+
+ /* TODO: Maybe we should verify that you can delete the file from the trash
+ before moving it? OTOH, that is hard, as it needs a recursive scan */
+
+ filename = g_build_filename (old_trash_dir, basename, NULL);
+ trashfile = g_build_filename (filesdir, trashname, NULL);
+ g_free (trashname);
+
+ if (g_rename (filename, trashfile) == -1)
+ {
+ char *display_name;
+
+ g_free (filename);
+ g_free (infofile);
+ g_free (trashfile);
+
+ display_name = g_filename_display_name (basename);
+
+ g_printerr ("Unable to trash file %s: %s\n",
+ display_name, g_strerror (errno));
+
+ g_free (display_name);
+
+ return FALSE;
+ }
+
+ g_free (filename);
+ g_free (trashfile);
+
+ /* TODO: Do we need to update mtime/atime here after the move? */
+
+ /* We don't know the original dirname of the file, so we'll just assume it
+ * was the desktop. This way, the file is easy to find again. */
+ original_name = g_build_filename (g_get_user_special_dir (G_USER_DIRECTORY_DESKTOP), basename);
+ original_name_escaped = escape_trash_name (original_name);
+ g_free (original_name);
+
+ {
+ time_t t;
+ struct tm now;
+ t = time (NULL);
+ localtime_r (&t, &now);
+ delete_time[0] = 0;
+ strftime(delete_time, sizeof (delete_time), "%Y-%m-%dT%H:%M:%S", &now);
+ }
+
+ data = g_strdup_printf ("[Trash Info]\nPath=%s\nDeletionDate=%s\n",
+ original_name_escaped, delete_time);
+
+ g_file_set_contents (infofile, data, -1, NULL);
+ g_free (infofile);
+ g_free (data);
+
+ g_free (original_name_escaped);
+
+ return TRUE;
+}
+
+int
+migrate_trash (void)
+{
+ gboolean had_problem;
+ char *old_trash_dir;
+ char *info_dir;
+ char *files_dir;
+ GError *error;
+ GDir *dir;
+ const char *file;
+
+ had_problem = FALSE;
+
+ old_trash_dir = g_build_filename (g_get_home_dir (), OLD_TRASH_DIR, NULL);
+
+ if (!g_file_test (old_trash_dir, G_FILE_TEST_IS_DIR))
+ {
+ g_free (old_trash_dir);
+ return 0;
+ }
+
+ if (!create_new_trash (&info_dir, &files_dir))
+ {
+ g_free (old_trash_dir);
+ return 1;
+ }
+
+ error = NULL;
+ dir = g_dir_open (old_trash_dir, 0, &error);
+ if (!dir)
+ {
+ char *display_name;
+
+ display_name = g_filename_display_name (old_trash_dir);
+ g_free (old_trash_dir);
+
+ g_printerr ("Unable to list files from %s: %s\n",
+ display_name, error->message);
+
+ g_free (display_name);
+ g_error_free (error);
+
+ return 1;
+ }
+
+ while (file = g_dir_read_name (dir))
+ {
+ had_problem = !move_file (old_trash_dir, file, info_dir, files_dir)
+ || had_problem;
+ }
+ g_dir_close (dir);
+
+ if (!had_problem)
+ g_rmdir (old_trash_dir);
+
+ g_free (old_trash_dir);
+
+ return 0;
+}
+
+#if 0
+int
+main (int argc,
+ char **argv)
+{
+ return migrate_trash ();
+}
+#endif
Added: branches/gnome-2-22/gnome-session/migrate-trash.h
==============================================================================
--- (empty file)
+++ branches/gnome-2-22/gnome-session/migrate-trash.h Mon Apr 7 23:43:54 2008
@@ -0,0 +1,6 @@
+#ifndef GSM_MIGRATE_TRASH_H
+#define GSM_MIGRATE_TRASH_H
+
+int migrate_trash (void);
+
+#endif /* GSM_MIGRATE_TRASH_H */
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]