diff options
| author | Tomas Bzatek <tbzatek@users.sourceforge.net> | 2009-12-13 14:36:33 +0100 |
|---|---|---|
| committer | Tomas Bzatek <tbzatek@users.sourceforge.net> | 2009-12-13 14:36:33 +0100 |
| commit | e42a4ff3031aa1c1aaf27aa34d9395fec185924b (patch) | |
| tree | 51987665008a0f7a28c1351aaa4bb2eb1e37c46f | |
| parent | 016687cc49c811589951ebd064a86bdde1405866 (diff) | |
| download | tuxcmd-modules-e42a4ff3031aa1c1aaf27aa34d9395fec185924b.tar.xz | |
Error system transformation to GErrorv0.6.74
| -rw-r--r-- | common/filelist-vfs-intf.c | 90 | ||||
| -rw-r--r-- | common/filelist-vfs-intf.h | 10 | ||||
| -rw-r--r-- | common/tuxcmd-vfs.h | 25 | ||||
| -rw-r--r-- | gvfs/gvfs.c | 638 | ||||
| -rw-r--r-- | libarchive/Makefile | 6 | ||||
| -rw-r--r-- | libarchive/libarchive.c | 200 | ||||
| -rw-r--r-- | unrar/Makefile | 6 | ||||
| -rw-r--r-- | unrar/unrar.c | 254 | ||||
| -rw-r--r-- | zip/Makefile | 6 | ||||
| -rw-r--r-- | zip/zip.cpp | 389 |
10 files changed, 843 insertions, 781 deletions
diff --git a/common/filelist-vfs-intf.c b/common/filelist-vfs-intf.c index e806334..afb7a85 100644 --- a/common/filelist-vfs-intf.c +++ b/common/filelist-vfs-intf.c @@ -20,6 +20,7 @@ #include <stdio.h> #include <string.h> #include <glib.h> +#include <gio/gio.h> #include "tuxcmd-vfs.h" #include "strutils.h" @@ -111,9 +112,12 @@ vfs_filelist_get_dir_size_break (struct VfsFilelistData *data) /* -------------------------------------------------------------------------------------- */ -static void -assign_file_info (struct PathTree* node, struct TVFSItem *Item, const char *reference_full_path, gboolean follow_symlinks, gboolean add_full_path) +static struct TVFSItem * +assign_file_info (struct PathTree* node, const char *reference_full_path, gboolean follow_symlinks, gboolean add_full_path) { + struct TVFSItem *Item; + + Item = g_malloc (sizeof (struct TVFSItem)); copy_vfs_item (node->data, Item); if (add_full_path && reference_full_path) { g_free (Item->FName); @@ -126,10 +130,11 @@ assign_file_info (struct PathTree* node, struct TVFSItem *Item, const char *refe Item->iPackedSize = node->symlink_target_data->iPackedSize; Item->ItemType = node->symlink_target_data->ItemType; } + return Item; } -TVFSResult -vfs_filelist_file_info (struct VfsFilelistData *data, const char *AFileName, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +vfs_filelist_file_info (struct VfsFilelistData *data, const char *AFileName, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { struct PathTree *node; @@ -137,35 +142,39 @@ vfs_filelist_file_info (struct VfsFilelistData *data, const char *AFileName, str node = filelist_tree_find_node_by_path (data->files, AFileName); if (node) { if (node->data) { - assign_file_info (node, Item, AFileName, FollowSymlinks, AddFullPath); - printf ("(II) VFSFileInfo: found file: '%s'\n", Item->FName); - return cVFS_OK; + printf ("(II) vfs_filelist_file_info: found file: '%s'\n", node->node); + return assign_file_info (node, AFileName, FollowSymlinks, AddFullPath); } else { - printf ("(EE) VFSFileInfo: node->data == NULL! \n"); - return cVFS_Failed; + printf ("(EE) vfs_filelist_file_info: node->data == NULL! \n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_INITIALIZED, "node->data == NULL"); + return NULL; } } else { - printf ("(EE) VFSFileInfo: file specified not found\n"); - return cVFS_No_More_Files; + printf ("(EE) vfs_filelist_file_info: file specified not found\n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "File specified not found."); + return NULL; } } else { - printf ("(EE) VFSFileInfo: Invalid pointers to data objects.\n"); - return cVFS_Failed; + printf ("(EE) vfs_filelist_file_info: Invalid pointers to data objects.\n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "Invalid pointers to data objects."); + return NULL; } } -TVFSResult -vfs_filelist_list_first (struct VfsFilelistData *data, const char *sDir, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +vfs_filelist_list_first (struct VfsFilelistData *data, const char *sDir, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { struct PathTree *node; char *full_path; + struct TVFSItem *Item; data->list_dir_index = -1; data->list_dir_node = NULL; if (sDir == NULL) { - printf ("(EE) VFSListFirst: sDir is NULL!\n"); - return cVFS_Failed; + printf ("(EE) vfs_filelist_list_first: sDir is NULL!\n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "NewPath is NULL"); + return NULL; } data->list_dir_index = 0; @@ -181,30 +190,33 @@ vfs_filelist_list_first (struct VfsFilelistData *data, const char *sDir, struct full_path = NULL; if (AddFullPath) full_path = g_build_filename (sDir, node->data->FName, NULL); - assign_file_info (node, Item, full_path, FollowSymlinks, AddFullPath); + Item = assign_file_info (node, full_path, FollowSymlinks, AddFullPath); g_free (full_path); - printf ("(II) VFSListFirst: found file: %s\n", Item->FName); - return cVFS_OK; + printf ("(II) vfs_filelist_list_first: found file: %s\n", Item->FName); + return Item; } else { - printf ("(II) VFSListFirst: no more files\n"); - return cVFS_No_More_Files; + printf ("(II) vfs_filelist_list_first: no more files\n"); + return NULL; } } else { - printf ("(EE) VFSListFirst: Directory '%s' not found.\n", sDir); - return cVFS_Failed; + printf ("(EE) vfs_filelist_list_first: Directory '%s' not found.\n", sDir); + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Directory '%s' not found.", sDir); + return NULL; } } -TVFSResult -vfs_filelist_list_next (struct VfsFilelistData *data, struct TVFSItem *Item) +struct TVFSItem * +vfs_filelist_list_next (struct VfsFilelistData *data, GError **error) { struct PathTree *node; char *full_path; + struct TVFSItem *Item; full_path = NULL; if (! data->list_dir_node) { - printf ("(EE) VFSListNext: data->list_dir_node is NULL!\n"); - return cVFS_Failed; + printf ("(EE) vfs_filelist_list_next: data->list_dir_node is NULL!\n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_INITIALIZED, "data->list_dir_node is NULL"); + return NULL; } data->list_dir_index++; @@ -212,36 +224,37 @@ vfs_filelist_list_next (struct VfsFilelistData *data, struct TVFSItem *Item) if (node) { if (data->add_full_path) full_path = g_build_filename (data->list_dir_path, node->data->FName, NULL); - assign_file_info (node, Item, full_path, data->follow_symlinks, data->add_full_path); + Item = assign_file_info (node, full_path, data->follow_symlinks, data->add_full_path); g_free (full_path); - printf ("(II) VFSListNext: found file: %s\n", Item->FName); - return cVFS_OK; + printf ("(II) vfs_filelist_list_next: found file: %s\n", Item->FName); + return Item; } else { - printf ("(II) VFSListNext: no more files\n"); - return cVFS_No_More_Files; + printf ("(II) vfs_filelist_list_next: no more files\n"); + return NULL; } } -TVFSResult -vfs_filelist_list_close (struct VfsFilelistData *data) +gboolean +vfs_filelist_list_close (struct VfsFilelistData *data, GError **error) { data->list_dir_index = -1; data->list_dir_node = NULL; g_free (data->list_dir_path); data->list_dir_path = NULL; - return cVFS_OK; + return TRUE; } /* -------------------------------------------------------------------------------------- */ char * -vfs_filelist_change_dir (struct VfsFilelistData *data, const char *NewPath) +vfs_filelist_change_dir (struct VfsFilelistData *data, const char *NewPath, GError **error) { char *ANewPath; if (NewPath == NULL) { - printf("(EE) VFSChangeDir: NewPath is NULL!\n"); + printf ("(EE) VFSChangeDir: NewPath is NULL!\n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "NewPath is NULL"); return NULL; } @@ -258,6 +271,7 @@ vfs_filelist_change_dir (struct VfsFilelistData *data, const char *NewPath) } else { printf ("(EE) VFSChangeDir: Directory '%s' not found.\n", ANewPath); g_free (ANewPath); + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Directory '%s' not found.", ANewPath); return NULL; } } diff --git a/common/filelist-vfs-intf.h b/common/filelist-vfs-intf.h index ff3eeef..d781e70 100644 --- a/common/filelist-vfs-intf.h +++ b/common/filelist-vfs-intf.h @@ -52,13 +52,13 @@ guint64 vfs_filelist_get_dir_size (struct VfsFilelistData *data, const char void vfs_filelist_get_dir_size_break (struct VfsFilelistData *data); gboolean vfs_filelist_file_exists (struct VfsFilelistData *data, const char *FileName, const long Use_lstat); -TVFSResult vfs_filelist_file_info (struct VfsFilelistData *data, const char *AFileName, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath); -TVFSResult vfs_filelist_list_first (struct VfsFilelistData *data, const char *sDir, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath); -TVFSResult vfs_filelist_list_next (struct VfsFilelistData *data, struct TVFSItem *Item); -TVFSResult vfs_filelist_list_close (struct VfsFilelistData *data); +struct TVFSItem * vfs_filelist_file_info (struct VfsFilelistData *data, const char *AFileName, gboolean FollowSymlinks, gboolean AddFullPath, GError **error); +struct TVFSItem * vfs_filelist_list_first (struct VfsFilelistData *data, const char *sDir, gboolean FollowSymlinks, gboolean AddFullPath, GError **error); +struct TVFSItem * vfs_filelist_list_next (struct VfsFilelistData *data, GError **error); +gboolean vfs_filelist_list_close (struct VfsFilelistData *data, GError **error); -char * vfs_filelist_change_dir (struct VfsFilelistData *data, const char *NewPath); +char * vfs_filelist_change_dir (struct VfsFilelistData *data, const char *NewPath, GError **error); diff --git a/common/tuxcmd-vfs.h b/common/tuxcmd-vfs.h index 2ced1b1..309b43c 100644 --- a/common/tuxcmd-vfs.h +++ b/common/tuxcmd-vfs.h @@ -27,10 +27,8 @@ extern "C" { #endif - #include <glib.h> -typedef int TVFSResult; /* Compatible with gio/GAskPasswordFlags */ typedef enum { @@ -43,6 +41,7 @@ typedef enum { VFS_ASK_PASSWORD_ARCHIVE_MODE = 1 << 15 } TVFSAskPasswordFlags; + /* Compatible with gio/GPasswordSave */ typedef enum { VFS_PASSWORD_SAVE_NEVER, @@ -50,6 +49,7 @@ typedef enum { VFS_PASSWORD_SAVE_PERMANENTLY } TVFSPasswordSave; + /* Module capability flags */ typedef enum { VFS_CAP_HANDLES_MULTIPLE_REQUESTS = 1 << 0, /* Multiple (background) operations; usually unsuitable for archives */ @@ -59,6 +59,7 @@ typedef enum { } TVFSModuleCapabilities; + typedef void (* TVFSLogFunc) (const char *s); typedef void * TVFSFileDes; @@ -66,7 +67,7 @@ typedef void * TVFSFileDes; /* Return FALSE to break the operation */ typedef gboolean (* TVFSProgressCallback) (guint64 position, - guint64 max, + GError *error, void *user_data); /* Return index of the choice selected or negative number when dialog has been cancelled */ @@ -94,24 +95,6 @@ typedef gboolean (* TVFSAskPasswordCallback) /* current version of the VFS API */ static const int cVFSVersion = 5; -/* error codes (TVFSResult) */ -enum { - cVFS_OK = 0, - cVFS_Failed = 1, /* also No such file */ - cVFS_Cancelled = 2, - cVFS_Not_Supported = 3, - cVFS_No_More_Files = 4, - cVFS_ReadErr = 5, - cVFS_WriteErr = 6, /* also Readonly FileSystem */ - cVFS_LoginFailed = 7, - cVFS_PermissionDenied = 8, - cVFS_NoSpaceLeft = 9, - cVFS_mallocFailed = 10, - cVFS_BadPassword = 11, - cVFS_MissingVolume = 12, - cVFS_CorruptedArchive = 13 -}; - /* open modes */ enum { diff --git a/gvfs/gvfs.c b/gvfs/gvfs.c index f62cfaa..a0de5cf 100644 --- a/gvfs/gvfs.c +++ b/gvfs/gvfs.c @@ -28,8 +28,8 @@ -#define VERSION "0.2.0" -#define BUILD_DATE "2009-11-21" +#define VERSION "0.2.1" +#define BUILD_DATE "2009-12-09" #define DEFAULT_BLOCK_SIZE 0x10000 /* 64kB */ #define CONST_DEFAULT_QUERY_INFO_ATTRIBUTES G_FILE_ATTRIBUTE_STANDARD_TYPE "," G_FILE_ATTRIBUTE_STANDARD_IS_SYMLINK "," \ @@ -50,7 +50,7 @@ struct TVFSGlobs { gboolean enum_add_full_path; GMainLoop *mount_main_loop; - TVFSResult mount_result; + GError *mount_error; int mount_try; gboolean ftp_anonymous; @@ -65,62 +65,6 @@ struct TVFSGlobs { -static TVFSResult -g_error_to_TVFSResult (GError *error) -{ - g_print ("g_error_to_TVFSResult: code = %d\n", error->code); - switch (error->code) { - case G_IO_ERROR_FAILED: - case G_IO_ERROR_NOT_FOUND: - return cVFS_Failed; - break; - case G_IO_ERROR_PERMISSION_DENIED: - return cVFS_PermissionDenied; - break; - case G_IO_ERROR_CANCELLED: - return cVFS_Cancelled; - break; - case G_IO_ERROR_NOT_SUPPORTED: - case G_IO_ERROR_FILENAME_TOO_LONG: - return cVFS_Not_Supported; - break; - case G_IO_ERROR_NO_SPACE: - return cVFS_NoSpaceLeft; - break; - case G_IO_ERROR_IS_DIRECTORY: - case G_IO_ERROR_NOT_REGULAR_FILE: - case G_IO_ERROR_NOT_SYMBOLIC_LINK: - case G_IO_ERROR_NOT_MOUNTABLE_FILE: - case G_IO_ERROR_INVALID_FILENAME: - case G_IO_ERROR_TOO_MANY_LINKS: - case G_IO_ERROR_INVALID_ARGUMENT: - case G_IO_ERROR_NOT_DIRECTORY: - case G_IO_ERROR_NOT_MOUNTED: - case G_IO_ERROR_ALREADY_MOUNTED: - case G_IO_ERROR_WRONG_ETAG: - case G_IO_ERROR_TIMED_OUT: - case G_IO_ERROR_WOULD_RECURSE: - case G_IO_ERROR_HOST_NOT_FOUND: - return cVFS_ReadErr; - break; - case G_IO_ERROR_EXISTS: - case G_IO_ERROR_NOT_EMPTY: - case G_IO_ERROR_CLOSED: - case G_IO_ERROR_PENDING: - case G_IO_ERROR_READ_ONLY: - case G_IO_ERROR_CANT_CREATE_BACKUP: - case G_IO_ERROR_BUSY: - case G_IO_ERROR_WOULD_BLOCK: - case G_IO_ERROR_WOULD_MERGE: - return cVFS_WriteErr; - break; - case G_IO_ERROR_FAILED_HANDLED: - default: - return cVFS_Failed; - } -} - - static void ask_password_cb (GMountOperation *op, const char *message, @@ -246,28 +190,22 @@ mount_done_cb (GObject *object, { struct TVFSGlobs *globs; gboolean succeeded; - GError *error = NULL; globs = (struct TVFSGlobs*) user_data; g_assert (globs != NULL); - succeeded = g_file_mount_enclosing_volume_finish (G_FILE (object), res, &error); + succeeded = g_file_mount_enclosing_volume_finish (G_FILE (object), res, &globs->mount_error); - if (! succeeded) { - g_print ("(EE) Error mounting location: %s\n", error->message); - globs->mount_result = g_error_to_TVFSResult (error); - g_error_free (error); - } - else { - globs->mount_result = cVFS_OK; + if (! succeeded) + g_print ("(EE) Error mounting location: %s\n", globs->mount_error->message); + else g_print ("(II) Mount successful.\n"); - } g_main_loop_quit (globs->mount_main_loop); } -static TVFSResult +static GError * vfs_handle_mount (struct TVFSGlobs *globs, GFile *file) { GMountOperation *op; @@ -277,7 +215,7 @@ vfs_handle_mount (struct TVFSGlobs *globs, GFile *file) op = g_mount_operation_new (); g_signal_connect (op, "ask-password", (GCallback)ask_password_cb, globs); g_signal_connect (op, "ask-question", (GCallback)ask_question_cb, globs); - globs->mount_result = cVFS_Failed; + globs->mount_error = NULL; globs->mount_try = 0; /* Inspiration taken from Bastien Nocera's http://svn.gnome.org/viewvc/totem-pl-parser/trunk/plparse/totem-disc.c?view=markup */ @@ -289,7 +227,7 @@ vfs_handle_mount (struct TVFSGlobs *globs, GFile *file) globs->mount_main_loop = NULL; g_object_unref (op); - return globs->mount_result; + return globs->mount_error; } @@ -407,13 +345,12 @@ VFSGetNetworkServices () } -TVFSResult -VFSOpenURI (struct TVFSGlobs *globs, const char *sURI) +gboolean +VFSOpenURI (struct TVFSGlobs *globs, const char *sURI, GError **error) { GFile *f, *f2; GFileInfo *info; - GError *error; - TVFSResult res; + GError *local_error; globs->file = NULL; globs->ftp_anonymous = FALSE; @@ -427,49 +364,49 @@ VFSOpenURI (struct TVFSGlobs *globs, const char *sURI) f = g_file_new_for_commandline_arg (sURI); while (1) { - error = NULL; + local_error = NULL; info = g_file_query_info (f, CONST_DEFAULT_QUERY_INFO_ATTRIBUTES, - G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &error); + G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &local_error); /* Fallback to parent directory if specified path doesn't exist */ - if (error && g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) { + if (local_error && g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) { f2 = g_file_get_parent (f); if (f2) { g_object_unref (f); f = f2; - g_error_free (error); + g_error_free (local_error); continue; } } /* Mount the target */ - if (error && g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_MOUNTED)) { - g_error_free (error); - error = NULL; - res = vfs_handle_mount (globs, f); - if (res != cVFS_OK) - return res; + if (local_error && g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_NOT_MOUNTED)) { + g_error_free (local_error); + local_error = vfs_handle_mount (globs, f); + if (local_error != NULL) { + g_propagate_error (error, local_error); + return FALSE; + } else continue; } /* Any other errors --> report */ - if (error) { - g_print ("(EE) VFSOpenURI: g_file_query_info() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + if (local_error) { + g_print ("(EE) VFSOpenURI: g_file_query_info() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (f); - return res; + return FALSE; } /* everything ok? */ break; } globs->file = f; - return cVFS_OK; + return TRUE; } -TVFSResult -VFSClose (struct TVFSGlobs *globs) +gboolean +VFSClose (struct TVFSGlobs *globs, GError **error) { g_print ("(II) VFSClose\n"); @@ -477,7 +414,7 @@ VFSClose (struct TVFSGlobs *globs) g_object_unref (globs->file); globs->file = NULL; - return cVFS_OK; + return TRUE; } @@ -531,12 +468,11 @@ VFSGetPathURI (struct TVFSGlobs *globs) } -TVFSResult +void VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize, gint64 *FSFree, char **FSLabel) { GFileInfo *info; GError *error; - TVFSResult res; if (FSSize) *FSSize = -1; @@ -546,44 +482,41 @@ VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize *FSLabel = NULL; if (globs->file == NULL) - return cVFS_Failed; + return; error = NULL; info = g_file_query_filesystem_info (globs->file, G_FILE_ATTRIBUTE_FILESYSTEM_SIZE "," G_FILE_ATTRIBUTE_FILESYSTEM_FREE, NULL, &error); if (error) { g_print ("(EE) VFSGetFileSystemInfo: %s\n", error->message); g_error_free (error); - res = cVFS_Failed; } else { if (FSSize) *FSSize = g_file_info_get_attribute_uint64 (info, G_FILE_ATTRIBUTE_FILESYSTEM_SIZE); if (FSFree) *FSFree = g_file_info_get_attribute_uint64 (info, G_FILE_ATTRIBUTE_FILESYSTEM_FREE); - res = cVFS_OK; } if (info) g_object_unref (info); - return res; } /**************************************************************************************************************************************/ /**************************************************************************************************************************************/ -TVFSResult -VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) +gboolean +VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath, GError **error) { GFile *f; GFileEnumerator *en; - GError *error, *error_shortcut; - TVFSResult res; + GError *local_error; GFileInfo *info; gchar *target_uri; if (globs->file == NULL) { g_print ("(EE) VFSChangeDir: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } g_print ("(II) VFSChangeDir: changing dir to '%s'\n", NewPath); @@ -591,20 +524,19 @@ VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) f = g_file_resolve_relative_path (globs->file, NewPath); if (f == NULL) { g_print ("(EE) VFSChangeDir: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } - res = cVFS_OK; while (1) { - error = NULL; + local_error = NULL; en = g_file_enumerate_children (f, CONST_DEFAULT_QUERY_INFO_ATTRIBUTES, - G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &error); + G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &local_error); /* if the target is shortcut, change the URI */ - if (error && g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_DIRECTORY)) { - error_shortcut = NULL; + if (local_error && g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_NOT_DIRECTORY)) { info = g_file_query_info (f, G_FILE_ATTRIBUTE_STANDARD_TARGET_URI, - G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &error_shortcut); + G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, NULL); if (info) { target_uri = g_strdup (g_file_info_get_attribute_string (info, G_FILE_ATTRIBUTE_STANDARD_TARGET_URI)); g_object_unref (info); @@ -613,31 +545,29 @@ VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) g_object_unref (f); f = g_file_new_for_uri (target_uri); g_free (target_uri); - g_error_free (error); + g_error_free (local_error); continue; } } - if (error_shortcut) - g_error_free (error_shortcut); } /* Mount the target */ - if (error && g_error_matches (error, G_IO_ERROR, G_IO_ERROR_NOT_MOUNTED)) { - g_error_free (error); - res = vfs_handle_mount (globs, f); - if (res != cVFS_OK) { + if (local_error && g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_NOT_MOUNTED)) { + g_error_free (local_error); + local_error = vfs_handle_mount (globs, f); + if (local_error != NULL) { g_object_unref (f); - return res; + g_propagate_error (error, local_error); + return FALSE; } else continue; } /* Any other errors --> report */ - if (error) { - g_print ("(EE) VFSChangeDir: g_file_enumerate_children() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + if (local_error) { + g_print ("(EE) VFSChangeDir: g_file_enumerate_children() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (f); - return res; + return FALSE; } /* everything ok? */ break; @@ -648,22 +578,23 @@ VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) g_object_unref (globs->file); globs->file = f; - return res; + return TRUE; } /**************************************************************************************************************************************/ /**************************************************************************************************************************************/ -static void -g_file_info_to_TVFSItem (GFileInfo *info, struct TVFSItem *Item, GFile *reference_file, gboolean follow_symlinks, gboolean add_full_path) +static struct TVFSItem * +g_file_info_to_TVFSItem (GFileInfo *info, GFile *reference_file, gboolean follow_symlinks, gboolean add_full_path) { GFileInfo *symlink_info = NULL; GError *error; + struct TVFSItem *Item; g_assert (info != NULL); - g_assert (Item != NULL); + Item = g_malloc0 (sizeof (struct TVFSItem)); if (add_full_path) { Item->FName = get_absolute_path (reference_file); if (Item->FName == NULL) @@ -727,55 +658,60 @@ g_file_info_to_TVFSItem (GFileInfo *info, struct TVFSItem *Item, GFile *referenc if (symlink_info) g_object_unref (symlink_info); + + return Item; } -TVFSResult -VFSListNext (struct TVFSGlobs *globs, struct TVFSItem *Item) + +struct TVFSItem * +VFSListNext (struct TVFSGlobs *globs, GError **error) { - GError *error; GFileInfo *info; - TVFSResult res; GFile *f; + GError *local_error; + struct TVFSItem *Item; if (globs->file == NULL) { g_print ("(EE) VFSListNext: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return NULL; } if (globs->enumerator == NULL) { g_print ("(EE) VFSListNext: globs->enumerator == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->enumerator == NULL"); + return NULL; } - error = NULL; - info = g_file_enumerator_next_file (globs->enumerator, NULL, &error); - if (error) { - g_print ("(EE) VFSListNext: g_file_enumerator_next_file() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); - return res; + local_error = NULL; + info = g_file_enumerator_next_file (globs->enumerator, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSListNext: g_file_enumerator_next_file() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + return FALSE; } - if (! error && ! info) - return cVFS_No_More_Files; + if (! info) + return NULL; f = g_file_get_child (globs->enumerated_file, g_file_info_get_name (info)); - g_file_info_to_TVFSItem (info, Item, f, globs->enum_follow_symlinks, globs->enum_add_full_path); + Item = g_file_info_to_TVFSItem (info, f, globs->enum_follow_symlinks, globs->enum_add_full_path); g_object_unref (f); g_object_unref (info); - return cVFS_OK; + return Item; } -TVFSResult -VFSListFirst (struct TVFSGlobs *globs, const char *sDir, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) + +struct TVFSItem * +VFSListFirst (struct TVFSGlobs *globs, const char *sDir, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { GFile *list_file; - GError *error; - TVFSResult res; + GError *local_error; list_file = g_file_resolve_relative_path (globs->file, sDir); if (! list_file) { g_print ("(EE) VFSListFirst: list_file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return NULL; } if (globs->enumerator == NULL || ! g_file_equal (globs->file, list_file)) { @@ -787,15 +723,14 @@ VFSListFirst (struct TVFSGlobs *globs, const char *sDir, struct TVFSItem *Item, if (globs->enumerated_file) g_object_unref (globs->enumerated_file); globs->enumerated_file = NULL; - error = NULL; + local_error = NULL; globs->enumerator = g_file_enumerate_children (list_file, CONST_DEFAULT_QUERY_INFO_ATTRIBUTES, - G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &error); - if (error) { - g_print ("(EE) VFSListFirst: g_file_enumerate_children() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSListFirst: g_file_enumerate_children() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (list_file); - return res; + return NULL; } globs->enumerated_file = g_object_ref (list_file); } @@ -803,320 +738,331 @@ VFSListFirst (struct TVFSGlobs *globs, const char *sDir, struct TVFSItem *Item, globs->enum_add_full_path = AddFullPath; g_object_unref (list_file); - return VFSListNext (globs, Item); + return VFSListNext (globs, error); } -TVFSResult -VFSListClose (struct TVFSGlobs *globs) + +gboolean +VFSListClose (struct TVFSGlobs *globs, GError **error) { - GError *error; - TVFSResult res; + GError *local_error; if (globs->enumerator == NULL) { g_print ("(EE) VFSListClose: globs->enumerator == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->enumerator == NULL"); + return FALSE; } g_print ("(II) VFSListClose\n"); - error = NULL; - g_file_enumerator_close (globs->enumerator, NULL, &error); + local_error = NULL; + g_file_enumerator_close (globs->enumerator, NULL, &local_error); g_object_unref (globs->enumerator); globs->enumerator = NULL; g_object_unref (globs->enumerated_file); globs->enumerated_file = NULL; - if (error) { - g_print ("(EE) VFSListClose: g_file_enumerator_close() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); - return res; + if (local_error) { + g_print ("(EE) VFSListClose: g_file_enumerator_close() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + return FALSE; } - return cVFS_OK; + return TRUE; } /**************************************************************************************************************************************/ /**************************************************************************************************************************************/ -TVFSResult -VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { GFile *f; - GError *error; + GError *local_error; GFileInfo *info; - TVFSResult res; + struct TVFSItem *Item; if (globs->file == NULL) { g_print ("(EE) VFSFileInfo: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return NULL; } f = g_file_resolve_relative_path (globs->file, AFileName); if (f == NULL) { g_print ("(EE) VFSMkDir: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return NULL; } - error = NULL; + local_error = NULL; info = g_file_query_info (f, CONST_DEFAULT_QUERY_INFO_ATTRIBUTES, - G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &error); - if (error) { - g_print ("(EE) VFSFileInfo: g_file_query_info() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSFileInfo: g_file_query_info() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (f); - return res; + return NULL; } - g_file_info_to_TVFSItem (info, Item, f, FollowSymlinks, AddFullPath); + Item = g_file_info_to_TVFSItem (info, f, FollowSymlinks, AddFullPath); + g_object_unref (info); g_object_unref (f); - return cVFS_OK; + return Item; } -TVFSResult -VFSMkDir (struct TVFSGlobs *globs, const char *sDirName) + +gboolean +VFSMkDir (struct TVFSGlobs *globs, const char *sDirName, GError **error) { GFile *f; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSMkDir: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } f = g_file_resolve_relative_path (globs->file, sDirName); if (f == NULL) { g_print ("(EE) VFSMkDir: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } - error = NULL; - g_file_make_directory (f, NULL, &error); + local_error = NULL; + g_file_make_directory (f, NULL, &local_error); g_object_unref (f); - if (error) { - g_print ("(EE) VFSMkDir: g_file_make_directory() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); - return res; + if (local_error) { + g_print ("(EE) VFSMkDir: g_file_make_directory() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + return FALSE; } - return cVFS_OK; + return TRUE; } -TVFSResult -VFSRemove (struct TVFSGlobs *globs, const char *APath) + +gboolean +VFSRemove (struct TVFSGlobs *globs, const char *APath, GError **error) { GFile *f; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSRemove: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } f = g_file_resolve_relative_path (globs->file, APath); if (f == NULL) { g_print ("(EE) VFSRemove: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } - error = NULL; - g_file_delete (f, NULL, &error); + local_error = NULL; + g_file_delete (f, NULL, &local_error); g_object_unref (f); - if (error) { - g_print ("(EE) VFSRemove: g_file_delete() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); - return res; + if (local_error) { + g_print ("(EE) VFSRemove: g_file_delete() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + return FALSE; } - return cVFS_OK; + return TRUE; } -TVFSResult -VFSRename (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName) + +gboolean +VFSRename (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, GError **error) { GFile *src, *dst; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSRename: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } src = g_file_resolve_relative_path (globs->file, sSrcName); if (src == NULL) { g_print ("(EE) VFSRename: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } g_print ("VFSRename: '%s' --> '%s'\n", sSrcName, sDstName); - error = NULL; - g_file_set_display_name (src, sDstName, NULL, &error); - if (error) { - g_print ("(WW) VFSRename: g_file_set_display_name() failed (\"%s\"), using fallback g_file_move()\n", error->message); - g_error_free (error); + local_error = NULL; + g_file_set_display_name (src, sDstName, NULL, &local_error); + if (local_error) { + g_print ("(WW) VFSRename: g_file_set_display_name() failed (\"%s\"), using fallback g_file_move()\n", local_error->message); + g_error_free (local_error); dst = g_file_resolve_relative_path (src, sDstName); if (dst == NULL) { g_print ("(EE) VFSRename: g_file_resolve_relative_path() failed.\n"); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path for target file."); g_object_unref (src); - return cVFS_Failed; + return FALSE; } - error = NULL; - g_file_move (src, dst, G_FILE_COPY_NO_FALLBACK_FOR_MOVE, NULL, NULL, NULL, &error); - if (error) { - g_print ("(EE) VFSRename: g_file_move() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + + local_error = NULL; + g_file_move (src, dst, G_FILE_COPY_NO_FALLBACK_FOR_MOVE, NULL, NULL, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSRename: g_file_move() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (src); g_object_unref (dst); - return res; + return FALSE; } g_object_unref (dst); } g_object_unref (src); - return cVFS_OK; + return TRUE; } -TVFSResult -VFSMakeSymLink (struct TVFSGlobs *globs, const char *NewFileName, const char *PointTo) + +gboolean +VFSMakeSymLink (struct TVFSGlobs *globs, const char *NewFileName, const char *PointTo, GError **error) { GFile *f; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSMakeSymLink: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } f = g_file_resolve_relative_path (globs->file, NewFileName); if (f == NULL) { g_print ("(EE) VFSMakeSymLink: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } - error = NULL; - g_file_make_symbolic_link (f, PointTo, NULL, &error); + local_error = NULL; + g_file_make_symbolic_link (f, PointTo, NULL, &local_error); g_object_unref (f); - if (error) { - g_print ("(EE) VFSMakeSymLink: g_file_make_symbolic_link() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); - return res; + if (local_error) { + g_print ("(EE) VFSMakeSymLink: g_file_make_symbolic_link() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + return FALSE; } - return cVFS_OK; + return TRUE; } -TVFSResult -VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode) + +gboolean +VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode, GError **error) { GFile *f; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSChmod: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } f = g_file_resolve_relative_path (globs->file, FileName); if (f == NULL) { g_print ("(EE) VFSChmod: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } -// g_print ("(II) VFSChmod (%s, %d): Going to set permissions on '%s'\n", FileName, Mode, g_file_get_uri (f)); - error = NULL; - g_file_set_attribute_uint32 (f, G_FILE_ATTRIBUTE_UNIX_MODE, Mode, G_FILE_QUERY_INFO_NONE, NULL, &error); + local_error = NULL; + g_file_set_attribute_uint32 (f, G_FILE_ATTRIBUTE_UNIX_MODE, Mode, G_FILE_QUERY_INFO_NONE, NULL, &local_error); g_object_unref (f); - if (error) { - g_print ("(EE) VFSChmod: g_file_set_attribute_uint32() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); - return res; + if (local_error) { + g_print ("(EE) VFSChmod: g_file_set_attribute_uint32() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + return FALSE; } - return cVFS_OK; + return TRUE; } -TVFSResult -VFSChown (struct TVFSGlobs *globs, const char *FileName, guint32 UID, guint32 GID) + +gboolean +VFSChown (struct TVFSGlobs *globs, const char *FileName, guint32 UID, guint32 GID, GError **error) { GFile *f; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSChown: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } f = g_file_resolve_relative_path (globs->file, FileName); if (f == NULL) { g_print ("(EE) VFSChown: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } - error = NULL; - g_file_set_attribute_uint32 (f, G_FILE_ATTRIBUTE_UNIX_UID, UID, G_FILE_QUERY_INFO_NONE, NULL, &error); - if (error) { - g_print ("(EE) VFSChown: g_file_set_attribute_uint32() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + local_error = NULL; + g_file_set_attribute_uint32 (f, G_FILE_ATTRIBUTE_UNIX_UID, UID, G_FILE_QUERY_INFO_NONE, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSChown: g_file_set_attribute_uint32() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (f); - return res; + return FALSE; } - error = NULL; - g_file_set_attribute_uint32 (f, G_FILE_ATTRIBUTE_UNIX_GID, GID, G_FILE_QUERY_INFO_NONE, NULL, &error); - if (error) { - g_print ("(EE) VFSChown: g_file_set_attribute_uint32() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + local_error = NULL; + g_file_set_attribute_uint32 (f, G_FILE_ATTRIBUTE_UNIX_GID, GID, G_FILE_QUERY_INFO_NONE, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSChown: g_file_set_attribute_uint32() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (f); - return res; + return FALSE; } g_object_unref (f); - return cVFS_OK; + return TRUE; } -TVFSResult -VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint32 atime) + +gboolean +VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint32 atime, GError **error) { GFile *f; - GError *error; - TVFSResult res; + GError *local_error; if (globs->file == NULL) { g_print ("(EE) VFSChangeTimes: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } f = g_file_resolve_relative_path (globs->file, APath); if (f == NULL) { g_print ("(EE) VFSChangeTimes: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path."); + return FALSE; } - error = NULL; - g_file_set_attribute_uint64 (f, G_FILE_ATTRIBUTE_TIME_MODIFIED, mtime, G_FILE_QUERY_INFO_NONE, NULL, &error); - if (error) { - g_print ("(EE) VFSChangeTimes: g_file_set_attribute_uint64() error: %s\n", error->message); - res = g_error_to_TVFSResult (error); - g_error_free (error); + /* TODO: add nanoseconds */ + /* TODO: change to g_file_set_attributes_from_info () */ + local_error = NULL; + g_file_set_attribute_uint64 (f, G_FILE_ATTRIBUTE_TIME_MODIFIED, mtime, G_FILE_QUERY_INFO_NONE, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSChangeTimes: g_file_set_attribute_uint64() error: %s\n", local_error->message); + g_propagate_error (error, local_error); g_object_unref (f); - return res; + return FALSE; } - error = NULL; - g_file_set_attribute_uint64 (f, G_FILE_ATTRIBUTE_TIME_ACCESS, atime, G_FILE_QUERY_INFO_NONE, NULL, &error); - if (error) { - g_print ("(EE) VFSChangeTimes: g_file_set_attribute_uint64() error: %s\n", error->message); - g_error_free (error); + local_error = NULL; + g_file_set_attribute_uint64 (f, G_FILE_ATTRIBUTE_TIME_ACCESS, atime, G_FILE_QUERY_INFO_NONE, NULL, &local_error); + if (local_error) { + g_print ("(EE) VFSChangeTimes: g_file_set_attribute_uint64() error: %s\n", local_error->message); + g_error_free (local_error); /* Silently drop the error, atime is not commonly supported on most systems */ } g_object_unref (f); - return cVFS_OK; + return TRUE; } @@ -1212,6 +1158,7 @@ VFSBreakGetDirSize (struct TVFSGlobs *globs) /**************************************************************************************************************************************/ /**************************************************************************************************************************************/ +#if 0 TVFSFileDes VFSOpenFile (struct TVFSGlobs *globs, const char *APath, int Mode, int *Error) { @@ -1246,6 +1193,8 @@ VFSWriteFile (struct TVFSGlobs *globs, TVFSFileDes FileDescriptor, gpointer Buff printf("(WW) VFSWriteFile: Not supported in GVFS plugin.\n"); return cVFS_Not_Supported; } +#endif + void VFSSetBlockSize (struct TVFSGlobs *globs, guint32 Value) @@ -1254,6 +1203,7 @@ VFSSetBlockSize (struct TVFSGlobs *globs, guint32 Value) globs->block_size = Value; } + gboolean VFSIsOnSameFS (struct TVFSGlobs *globs, const char *Path1, const char *Path2, gboolean FollowSymlinks) { @@ -1313,6 +1263,7 @@ VFSIsOnSameFS (struct TVFSGlobs *globs, const char *Path1, const char *Path2, gb return res; } + gboolean VFSTwoSameFiles (struct TVFSGlobs *globs, const char *Path1, const char *Path2, gboolean FollowSymlinks) { @@ -1361,51 +1312,48 @@ vfs_copy_progress_callback (goffset current_num_bytes, globs = (struct TVFSGlobs *)user_data; if (globs->callback_progress) { - if (! globs->callback_progress (current_num_bytes, total_num_bytes, globs->callback_data)) + if (! globs->callback_progress (current_num_bytes, NULL, globs->callback_data)) g_cancellable_cancel (globs->cancellable); } } #define TUXCMD_DEFAULT_COPY_FLAGS G_FILE_COPY_OVERWRITE | G_FILE_COPY_NOFOLLOW_SYMLINKS | G_FILE_COPY_ALL_METADATA -TVFSResult -VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { GFile *src, *dst; - GError *error; - TVFSResult res; - + GError *local_error; + gboolean res; if (globs->file == NULL) { g_print ("(EE) VFSCopyToLocal: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } g_print ("(II) VFSCopyToLocal: '%s' --> '%s'\n", sSrcName, sDstName); - src = g_file_resolve_relative_path (globs->file, sSrcName); if (src == NULL) { g_print ("(EE) VFSCopyToLocal: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path for source file."); + return FALSE; } dst = g_file_new_for_path (sDstName); if (dst == NULL) { g_print ("(EE) VFSCopyToLocal: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot get target file."); + return FALSE; } + res = TRUE; + local_error = NULL; globs->cancellable = g_cancellable_new (); - - res = cVFS_OK; - error = NULL; - g_file_copy (src, dst, TUXCMD_DEFAULT_COPY_FLAGS, globs->cancellable, vfs_copy_progress_callback, globs, &error); - if (error) { - g_print ("(EE) VFSCopyToLocal: g_file_copy() error: %s\n", error->message); -// res = g_error_to_TVFSResult (error); - if (error->code == G_IO_ERROR_CANCELLED) - res = cVFS_Cancelled; - else res = cVFS_ReadErr; - g_error_free (error); + g_file_copy (src, dst, TUXCMD_DEFAULT_COPY_FLAGS, globs->cancellable, vfs_copy_progress_callback, globs, &local_error); + if (local_error) { + g_print ("(EE) VFSCopyToLocal: g_file_copy() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + res = FALSE; } g_object_unref (globs->cancellable); @@ -1414,45 +1362,45 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN return res; } -TVFSResult -VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) + +gboolean +VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { GFile *src, *dst; - GError *error; - TVFSResult res; - + GError *local_error; + gboolean res; if (globs->file == NULL) { g_print ("(EE) VFSCopyFromLocal: globs->file == NULL !\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "globs->file == NULL"); + return FALSE; } g_print ("(II) VFSCopyFromLocal: '%s' --> '%s'\n", sSrcName, sDstName); - src = g_file_new_for_path (sSrcName); if (src == NULL) { g_print ("(EE) VFSCopyFromLocal: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot get source file."); + return FALSE; } dst = g_file_resolve_relative_path (globs->file, sDstName); if (dst == NULL) { g_print ("(EE) VFSCopyFromLocal: g_file_resolve_relative_path() failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Cannot resolve relative path for target file."); + return FALSE; } globs->cancellable = g_cancellable_new (); - res = cVFS_OK; - error = NULL; + res = TRUE; + local_error = NULL; + globs->cancellable = g_cancellable_new (); /* FIXME: Appending not supported */ - g_file_copy (src, dst, TUXCMD_DEFAULT_COPY_FLAGS, globs->cancellable, vfs_copy_progress_callback, globs, &error); - if (error) { - g_print ("(EE) VFSCopyFromLocal: g_file_copy() error: %s\n", error->message); -// res = g_error_to_TVFSResult (error); - if (error->code == G_IO_ERROR_CANCELLED) - res = cVFS_Cancelled; - else res = cVFS_WriteErr; - g_error_free (error); + g_file_copy (src, dst, TUXCMD_DEFAULT_COPY_FLAGS, globs->cancellable, vfs_copy_progress_callback, globs, &local_error); + if (local_error) { + g_print ("(EE) VFSCopyFromLocal: g_file_copy() error: %s\n", local_error->message); + g_propagate_error (error, local_error); + res = FALSE; } g_object_unref (globs->cancellable); diff --git a/libarchive/Makefile b/libarchive/Makefile index 7604186..06bbd65 100644 --- a/libarchive/Makefile +++ b/libarchive/Makefile @@ -20,7 +20,7 @@ VFS_OBJECTS = libarchive.o .SUFFIXES: .c .c.o: - $(CC) $(CFLAGS) `pkg-config glib-2.0 --cflags` -c $< + $(CC) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --cflags` -c $< all: static @@ -29,11 +29,11 @@ LIBARCHIVE_LIBS_EXT = `grep "$(DIR_LIBARCHIVE)/Makefile" -e '^LIBS = -l' | sed ' shared: CFLAGS += -DMODULE_SHARED shared: $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) - $(CC) -shared -o libarchive_plugin.so $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) $(CFLAGS) `pkg-config glib-2.0 --libs` -larchive + $(CC) -shared -o libarchive_plugin.so $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --libs` -larchive static: CFLAGS += -I$(DIR_LIBARCHIVE) -I$(DIR_LIBARCHIVE)/libarchive static: lib_libarchive_compile $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) - $(CC) -shared -o libarchive_plugin.so $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) $(DIR_LIBARCHIVE)/.libs/libarchive.a $(CFLAGS) `pkg-config glib-2.0 --libs` $(LIBARCHIVE_LIBS_EXT) + $(CC) -shared -o libarchive_plugin.so $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) $(DIR_LIBARCHIVE)/.libs/libarchive.a $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --libs` $(LIBARCHIVE_LIBS_EXT) lib_libarchive_compile: @which uudecode > /dev/null || exit 1; diff --git a/libarchive/libarchive.c b/libarchive/libarchive.c index 6c6c59c..cadd6a0 100644 --- a/libarchive/libarchive.c +++ b/libarchive/libarchive.c @@ -1,5 +1,5 @@ /* libarchive plugin for Tux Commander - * version 0.2.1, designed for libarchive v2.5.5 - v2.7.1 (recommended) + * version 0.2.2, designed for libarchive v2.5.5 - v2.7.1 (recommended) * Copyright (C) 2008-2009 Tomas Bzatek <tbzatek@users.sourceforge.net> * Check for updates on tuxcmd.sourceforge.net * @@ -30,6 +30,7 @@ #include <errno.h> #include <fcntl.h> #include <glib.h> +#include <gio/gio.h> #include "tuxcmd-vfs.h" #include "vfsutils.h" @@ -52,8 +53,8 @@ #endif -#define MODULE_VERSION "0.2.1" -#define MODULE_BUILD_DATE "2009-11-29" +#define MODULE_VERSION "0.2.2" +#define MODULE_BUILD_DATE "2009-12-12" #define DEFAULT_BLOCK_SIZE 65536 @@ -257,8 +258,8 @@ char *formats; /**************************************************************************************************************************************/ /**************************************************************************************************************************************/ -static TVFSResult -libarchive_open (struct archive **a, const char *filename, guint32 block_size) +static gboolean +libarchive_open (struct archive **a, const char *filename, guint32 block_size, GError **error) { int r; @@ -268,24 +269,25 @@ libarchive_open (struct archive **a, const char *filename, guint32 block_size) archive_read_support_compression_all (*a); archive_read_support_format_all (*a); - r = archive_read_open_file (*a, filename, block_size); + r = archive_read_open_filename (*a, filename, block_size); if (r) { fprintf (stderr, "(EE) libarchive_open: error occured when opening archive: %s\n", archive_error_string (*a)); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, g_io_error_from_errno (archive_errno (*a)), archive_error_string (*a)); + return FALSE; } - return cVFS_OK; + return TRUE; } -TVFSResult -VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) +gboolean +VFSOpenArchive (struct TVFSGlobs *globs, const char *sName, GError **error) { - TVFSResult Result; struct archive *a; struct archive_entry *entry; struct TVFSItem *item; int r; char *s; guint64 inode_no; + gboolean res; globs->files = filelist_tree_new (); globs->vfs_filelist = vfs_filelist_new (globs->files); @@ -294,8 +296,8 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) globs->total_size = 0; fprintf (stderr, "(--) VFSOpenArchive: trying to open archive '%s'...\n", globs->archive_path); - Result = libarchive_open (&a, globs->archive_path, globs->block_size); - if (Result == cVFS_OK) { + res = libarchive_open (&a, globs->archive_path, globs->block_size, error); + if (res) { inode_no = 0; for (;;) { entry = NULL; @@ -308,7 +310,8 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) } else if (r != ARCHIVE_OK) { fprintf (stderr, "(EE) VFSOpenArchive: error occured while reading archive: '%s'\n", archive_error_string (a)); - Result = cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, g_io_error_from_errno (archive_errno (a)), archive_error_string (a)); + res = FALSE; break; } @@ -393,12 +396,12 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) printf ("\n\nList of items:\n"); filelist_tree_print (globs->files); - return Result; + return res; } -TVFSResult -VFSClose (struct TVFSGlobs *globs) +gboolean +VFSClose (struct TVFSGlobs *globs, GError **error) { if (globs) { fprintf (stderr, "(II) VFSClose: Freeing objects...\n"); @@ -409,7 +412,7 @@ VFSClose (struct TVFSGlobs *globs) g_free (globs->archive_path); g_free (globs->curr_dir); } - return cVFS_OK; + return TRUE; } @@ -420,7 +423,7 @@ VFSGetPath (struct TVFSGlobs *globs) } -TVFSResult +void VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize, gint64 *FSFree, char **FSLabel) { if (FSSize) @@ -429,24 +432,21 @@ VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize *FSFree = 0; if (FSLabel) *FSLabel = NULL; - return cVFS_OK; } /******************************************************************************************************/ -TVFSResult -VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) +gboolean +VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath, GError **error) { - if (NewPath == NULL) { - printf("(EE) VFSChangeDir: NewPath is NULL!\n"); - return cVFS_Failed; - } + char *s; - globs->curr_dir = vfs_filelist_change_dir (globs->vfs_filelist, NewPath); - if (globs->curr_dir) - return cVFS_OK; - else - return cVFS_Failed; + s = vfs_filelist_change_dir (globs->vfs_filelist, NewPath, error); + if (s) { + globs->curr_dir = s; + return TRUE; + } else + return FALSE; } @@ -460,41 +460,35 @@ VFSGetPasswordRequired (struct TVFSGlobs *globs) /******************************************************************************************************/ -TVFSResult -VFSListFirst (struct TVFSGlobs *globs, const char *sDir, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSListFirst (struct TVFSGlobs *globs, const char *sDir, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { - if (sDir == NULL) { - printf("(EE) VFSListFirst: sDir is NULL!\n"); - return cVFS_Failed; - } printf ("(--) VFSListFirst: Going to list all items in '%s'\n", sDir); - return vfs_filelist_list_first (globs->vfs_filelist, sDir, Item, FollowSymlinks, AddFullPath); + return vfs_filelist_list_first (globs->vfs_filelist, sDir, FollowSymlinks, AddFullPath, error); } -TVFSResult -VFSListNext (struct TVFSGlobs *globs, struct TVFSItem *Item) +struct TVFSItem * +VFSListNext (struct TVFSGlobs *globs, GError **error) { - return vfs_filelist_list_next (globs->vfs_filelist, Item); + return vfs_filelist_list_next (globs->vfs_filelist, error); } -TVFSResult -VFSListClose (struct TVFSGlobs *globs) +gboolean +VFSListClose (struct TVFSGlobs *globs, GError **error) { - return vfs_filelist_list_close (globs->vfs_filelist); + return vfs_filelist_list_close (globs->vfs_filelist, error); } /******************************************************************************************************/ -TVFSResult -VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { printf ("(--) VFSFileInfo: requested info for object '%s'\n", AFileName); - if (! globs) - return cVFS_Failed; - return vfs_filelist_file_info (globs->vfs_filelist, AFileName, Item, FollowSymlinks, AddFullPath); + return vfs_filelist_file_info (globs->vfs_filelist, AFileName, FollowSymlinks, AddFullPath, error); } @@ -525,6 +519,7 @@ VFSBreakGetDirSize (struct TVFSGlobs *globs) /** Methods modifying the archive */ /************** ****************/ +#if 0 TVFSResult VFSMkDir (struct TVFSGlobs *globs, const char *sDirName) { printf ("(WW) VFSMkDir: Not supported in libarchive plugin.\n"); @@ -566,12 +561,13 @@ TVFSResult VFSChangeTimes (struct TVFSGlobs *globs, char *APath, guint32 mtime, printf ("(WW) VFSChangeTimes: Not supported in libarchive plugin.\n"); return cVFS_Not_Supported; } - +#endif /******************************************************************************************************/ /************** **/ +#if 0 TVFSFileDes VFSOpenFile(struct TVFSGlobs *globs, const char *APath, int Mode, int *Error) { *Error = cVFS_Not_Supported; @@ -600,6 +596,7 @@ int VFSWriteFile(struct TVFSGlobs *globs, TVFSFileDes FileDescriptor, void *Buff *Error = cVFS_Not_Supported; return 0; } +#endif void VFSSetBlockSize (struct TVFSGlobs *globs, guint32 Value) @@ -632,8 +629,8 @@ VFSTwoSameFiles (struct TVFSGlobs *globs, const char *Path1, const char *Path2, * The following code has been stolen from archive_read_data_into_fd.c (libarchive sources) and modified to allow progress callbacks * Quote: "This implementation minimizes copying of data and is sparse-file aware." **/ -static TVFSResult -my_archive_read_data_into_fd (struct TVFSGlobs *globs, struct archive *a, struct archive_entry *entry, const char *sDstName, size_t max_block, gboolean Append) +static gboolean +my_archive_read_data_into_fd (struct TVFSGlobs *globs, struct archive *a, struct archive_entry *entry, const char *sDstName, size_t max_block, gboolean Append, GError **error) { int r; int fd; @@ -644,6 +641,7 @@ my_archive_read_data_into_fd (struct TVFSGlobs *globs, struct archive *a, struct off_t output_offset; guint64 file_size; gboolean cancel = FALSE; + int saved_errno; printf ("(II) my_archive_read_data_into_fd: extracting to '%s', Append = %d\n", sDstName, Append); @@ -654,8 +652,10 @@ my_archive_read_data_into_fd (struct TVFSGlobs *globs, struct archive *a, struct fd = open (sDstName, O_CREAT | O_WRONLY | O_TRUNC, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); if (fd < 0) { - fprintf (stderr, "(EE) my_archive_read_data_into_fd: error occured while extracting data: %s\n", strerror (errno)); - return cVFS_Failed; + saved_errno = errno; + fprintf (stderr, "(EE) my_archive_read_data_into_fd: error occured while extracting data: %s\n", strerror (saved_errno)); + g_set_error (error, G_IO_ERROR, g_io_error_from_errno (saved_errno), "Error extracting data: %s", g_strerror (saved_errno)); + return FALSE; } total_written = 0; @@ -676,8 +676,11 @@ my_archive_read_data_into_fd (struct TVFSGlobs *globs, struct archive *a, struct bytes_to_write = max_block; bytes_written = write (fd, p, bytes_to_write); if (bytes_written < 0) { - fprintf (stderr, "(EE) my_archive_read_data_into_fd: error occured while extracting data: %s\n", strerror (errno)); - return cVFS_Failed; + saved_errno = errno; + fprintf (stderr, "(EE) my_archive_read_data_into_fd: error occured while extracting data: %s\n", strerror (saved_errno)); + g_set_error (error, G_IO_ERROR, g_io_error_from_errno (saved_errno), "Error writing data: %s", g_strerror (saved_errno)); + close (fd); + return FALSE; } output_offset += bytes_written; total_written += bytes_written; @@ -686,48 +689,57 @@ my_archive_read_data_into_fd (struct TVFSGlobs *globs, struct archive *a, struct log (" (II) my_archive_read_data_into_fd: bytes_written = %zd, total_written = %zd\n", bytes_written, total_written); if (globs->callback_progress) - if (! globs->callback_progress (total_written, file_size, globs->callback_data)) { + if (! globs->callback_progress (total_written, NULL, globs->callback_data)) { cancel = TRUE; break; } } } - if (close (fd) || (r != ARCHIVE_OK && r != ARCHIVE_EOF)) { + if (r != ARCHIVE_OK && r != ARCHIVE_EOF) { fprintf (stderr, "(EE) my_archive_read_data_into_fd: error closing extracted file: %s\n", strerror (errno)); - return cVFS_WriteErr; + g_set_error_literal (error, G_IO_ERROR, g_io_error_from_errno (archive_errno (a)), archive_error_string (a)); + close (fd); + return FALSE; + } + if (close (fd)) { + saved_errno = errno; + fprintf (stderr, "(EE) my_archive_read_data_into_fd: error closing extracted file: %s\n", strerror (errno)); + g_set_error (error, G_IO_ERROR, g_io_error_from_errno (saved_errno), "Error closing extracted file: %s", g_strerror (saved_errno)); + return FALSE; } if (cancel) { if (unlink (sDstName)) fprintf (stderr, "(EE) my_archive_read_data_into_fd: error unlinking cancelled extraction: %s\n", strerror (errno)); - return cVFS_Cancelled; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CANCELLED, "Operation has been cancelled."); + return FALSE; } printf ("(II) my_archive_read_data_into_fd: done.\n"); - return cVFS_OK; + return TRUE; } -TVFSResult -VFSStartCopyOperation (struct TVFSGlobs *globs) +gboolean +VFSStartCopyOperation (struct TVFSGlobs *globs, GError **error) { - TVFSResult Result; - - g_return_val_if_fail (globs != NULL, cVFS_Failed); - g_return_val_if_fail (globs->op_archive == NULL, cVFS_Failed); + if (globs->op_archive != NULL) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_ALREADY_MOUNTED, "globs->op_archive != NULL"); + return FALSE; + } printf ("(II) VFSStartCopyOperation: opening archive '%s'\n", globs->archive_path); - Result = libarchive_open (&globs->op_archive, globs->archive_path, globs->block_size); - - return Result; + return libarchive_open (&globs->op_archive, globs->archive_path, globs->block_size, error); } -TVFSResult -VFSStopCopyOperation (struct TVFSGlobs *globs) +gboolean +VFSStopCopyOperation (struct TVFSGlobs *globs, GError **error) { - g_return_val_if_fail (globs != NULL, cVFS_Failed); - g_return_val_if_fail (globs->op_archive != NULL, cVFS_Failed); + if (globs->op_archive == NULL) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_ALREADY_MOUNTED, "globs->op_archive == NULL"); + return FALSE; + } printf ("(II) VFSStopCopyOperation: closing archive.\n"); @@ -735,26 +747,29 @@ VFSStopCopyOperation (struct TVFSGlobs *globs) archive_read_finish (globs->op_archive); globs->op_archive = NULL; - return cVFS_OK; + return TRUE; } -TVFSResult -VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { struct PathTree *node; const char *src; - TVFSResult Result; struct archive_entry *entry; int r; gboolean found; + gboolean res; - g_return_val_if_fail (globs->op_archive != NULL, cVFS_ReadErr); - + if (globs->op_archive == NULL) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "globs->op_archive == NULL"); + return FALSE; + } if (sSrcName == NULL || sDstName == NULL || strlen (sSrcName) < 1 || strlen (sDstName) < 1) { printf ("(EE) VFSCopyToLocal: The value of 'sSrcName' or 'sDstName' is NULL or empty\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "The value of 'sSrcName' or 'sDstName' is NULL or empty."); + return FALSE; } printf ("(II) VFSCopyToLocal: copying file '%s' out to '%s'\n", sSrcName, sDstName); @@ -762,7 +777,8 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN node = filelist_tree_find_node_by_path (globs->files, sSrcName); if (! node) { fprintf (stderr, "(EE) VFSCopyToLocal: cannot find file '%s'\n", sSrcName); - return cVFS_ReadErr; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "cannot find file '%s'", sSrcName); + return FALSE; } src = node->original_pathstr; @@ -774,7 +790,7 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN found = FALSE; - Result = cVFS_ReadErr; + res = TRUE; for (;;) { entry = NULL; @@ -787,32 +803,34 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN } else if (r != ARCHIVE_OK) { fprintf (stderr, "(EE) VFSCopyToLocal: error occured while reading archive: '%s'\n", archive_error_string (globs->op_archive)); - Result = cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, g_io_error_from_errno (archive_errno (globs->op_archive)), archive_error_string (globs->op_archive)); break; } if (g_strcmp0 (src, archive_entry_pathname (entry)) == 0) { found = TRUE; - Result = my_archive_read_data_into_fd (globs, globs->op_archive, entry, sDstName, globs->block_size, Append); + res = my_archive_read_data_into_fd (globs, globs->op_archive, entry, sDstName, globs->block_size, Append, error); break; } } - if (! found && Result == cVFS_OK) { + if (! found && res) { fprintf (stderr, "(EE) VFSCopyToLocal: file not found in archive.\n"); - Result = cVFS_ReadErr; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "File not found in archive."); + res = FALSE; } fprintf (stderr, "(II) VFSCopyToLocal: finished. \n"); - return Result; + return res; } -TVFSResult -VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { printf ("(WW) VFSCopyFromLocal: Not supported in libarchive plugin.\n"); - return cVFS_Not_Supported; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, "Not supported in libarchive plugin."); + return FALSE; } diff --git a/unrar/Makefile b/unrar/Makefile index 4e930da..e822800 100644 --- a/unrar/Makefile +++ b/unrar/Makefile @@ -39,15 +39,15 @@ VFS_OBJECTS = unrar.o rarlog.o .SUFFIXES: .c .cpp .c.o: - $(CC) $(CFLAGS) `pkg-config glib-2.0 --cflags` -c $< + $(CC) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --cflags` -c $< .cpp.o: - $(CPP) $(CFLAGS) `pkg-config glib-2.0 --cflags` -c $< + $(CPP) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --cflags` -c $< all shared static: libunrar_plugin.so libunrar_plugin.so: libunrar $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) - $(CPP) -shared -o libunrar_plugin.so $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) $(UNRAR_OBJECTS) $(UNRAR_LIB_OBJ) $(CFLAGS) `pkg-config glib-2.0 --libs` + $(CPP) -shared -o libunrar_plugin.so $(VFS_COMMON_OBJECTS) $(VFS_OBJECTS) $(UNRAR_OBJECTS) $(UNRAR_LIB_OBJ) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --libs` libunrar: ( cd $(DIR_UNRAR) && make -f ../Makefile.unrar ) || exit 1 diff --git a/unrar/unrar.c b/unrar/unrar.c index 1d5a595..a022775 100644 --- a/unrar/unrar.c +++ b/unrar/unrar.c @@ -1,5 +1,5 @@ /* UNRAR plugin for Tux Commander - * version 0.4.1, designed for unrar v3.8.2 + * version 0.4.2, designed for unrar v3.8.2 * Copyright (C) 2007-2009 Tomas Bzatek <tbzatek@users.sourceforge.net> * Check for updates on tuxcmd.sourceforge.net * @@ -31,6 +31,7 @@ #include <errno.h> #include <unistd.h> #include <glib.h> +#include <gio/gio.h> #include "tuxcmd-vfs.h" #include "vfsutils.h" @@ -56,8 +57,8 @@ enum HOST_SYSTEM { }; -#define VERSION "0.4.1" -#define BUILD_DATE "2009-11-29" +#define VERSION "0.4.2" +#define BUILD_DATE "2009-12-12" #define DEFAULT_BLOCK_SIZE 65536 @@ -83,7 +84,6 @@ struct TVFSGlobs { guint64 total_size; - guint64 extract_file_size; guint64 extract_done; gboolean extract_cancelled; @@ -255,7 +255,7 @@ unrar_callback (UINT msg, LONG UserData, LONG P1, LONG P2) // long int res = globs->extract_callback_func((u_int64_t)P1, (u_int64_t)((u_int64_t)P1 + (u_int64_t)P2), globs->extract_callback_data); globs->extract_done += P2; - gboolean res = globs->callback_progress(globs->extract_done, globs->extract_file_size, globs->callback_data); + gboolean res = globs->callback_progress(globs->extract_done, NULL, globs->callback_data); // fprintf(stderr, " (II) unrar_callback: res = %d \n", res); if (! res ) { @@ -317,6 +317,7 @@ unrar_process_data_proc (unsigned char *Addr, int Size) return 0; } +/* ----------------------------------------------------------------------------------------------------------- */ static time_t rar_time_to_unix (unsigned int FileTime) @@ -334,17 +335,68 @@ rar_time_to_unix (unsigned int FileTime) } +/* TODO: find proper verbose explanation for each error. */ +static void +rar_error_to_gerror (int code, GError **error) +{ + switch (code) { + case ERAR_END_ARCHIVE: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED, "Unexpected end of archive."); + break; + case ERAR_NO_MEMORY: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Memory allocation failed."); + break; + case ERAR_BAD_DATA: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Bad data."); + break; + case ERAR_BAD_ARCHIVE: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Bad archive."); + break; + case ERAR_UNKNOWN_FORMAT: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "Unknown format."); + break; + case ERAR_EOPEN: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Open error."); + break; + case ERAR_ECREATE: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_PERMISSION_DENIED, "Create error."); + break; + case ERAR_ECLOSE: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED, "Close error."); + break; + case ERAR_EREAD: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Read error."); + break; + case ERAR_EWRITE: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Write error."); + break; + case ERAR_SMALL_BUF: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "Small buffer error."); + break; + case ERAR_UNKNOWN: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_UNKNOWN, "Unknown error."); + break; + case ERAR_MISSING_PASSWORD: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_PERMISSION_DENIED, "Missing password."); + break; + default: + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Operation failed."); + break; + } +} + + /* ----------------------------------------------------------------------------------------------------------- */ -TVFSResult -VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) +gboolean +VFSOpenArchive (struct TVFSGlobs *globs, const char *sName, GError **error) { - TVFSResult Result; HANDLE PASCAL handle; struct RAROpenArchiveDataEx *archive_data; guint64 inode_no; + gboolean Result; - Result = cVFS_OK; + Result = TRUE; globs->files = filelist_tree_new (); globs->vfs_filelist = vfs_filelist_new (globs->files); @@ -447,9 +499,12 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) // printf("\nRARReadHeader result = %d\n", res); if (res != ERAR_END_ARCHIVE || globs->volume_missing_abort) { fprintf (stderr, "(EE) VFSOpenArchive: RARReadHeader result = %d\n", res); - Result = cVFS_Failed; + rar_error_to_gerror (res, error); + Result = FALSE; +/* TODO: if (res == ERAR_MISSING_PASSWORD || (res == ERAR_BAD_DATA && globs->failed_passwd_callback)) Result = cVFS_BadPassword; +*/ } free (header); @@ -458,7 +513,8 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) fprintf (stderr, "(EE) VFSOpenArchive: RARCloseArchive result = %d\n", res); } else { fprintf (stderr, "(EE) VFSOpenArchive: error occured when opening archive: OpenResult = %d\n", archive_data->OpenResult); - Result = cVFS_Failed; + rar_error_to_gerror (archive_data->OpenResult, error); + Result = FALSE; } free (archive_data); @@ -472,8 +528,8 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) } -TVFSResult -VFSClose (struct TVFSGlobs *globs) +gboolean +VFSClose (struct TVFSGlobs *globs, GError **error) { if (globs) { fprintf (stderr, "(II) VFSClose: Freeing objects...\n"); @@ -485,7 +541,7 @@ VFSClose (struct TVFSGlobs *globs) g_free (globs->curr_dir); g_free (globs->password); } - return cVFS_OK; + return TRUE; } char * @@ -494,7 +550,7 @@ VFSGetPath (struct TVFSGlobs *globs) return include_trailing_path_sep (globs->curr_dir); } -TVFSResult +void VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize, gint64 *FSFree, char **FSLabel) { if (FSSize) @@ -503,25 +559,23 @@ VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize *FSFree = 0; if (FSLabel) *FSLabel = NULL; - return cVFS_OK; } /******************************************************************************************************/ -TVFSResult -VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) +gboolean +VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath, GError **error) { - if (NewPath == NULL) { - printf ("(EE) VFSChangeDir: NewPath is NULL!\n"); - return cVFS_Failed; - } + char *s; - globs->curr_dir = vfs_filelist_change_dir (globs->vfs_filelist, NewPath); - if (globs->curr_dir) - return cVFS_OK; + s = vfs_filelist_change_dir (globs->vfs_filelist, NewPath, error); + if (s) { + globs->curr_dir = s; + return TRUE; + } else - return cVFS_Failed; + return FALSE; } gboolean @@ -544,41 +598,35 @@ VFSResetPassword (struct TVFSGlobs *globs) /******************************************************************************************************/ -TVFSResult -VFSListFirst (struct TVFSGlobs *globs, const char *sDir, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSListFirst (struct TVFSGlobs *globs, const char *sDir, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { - if (sDir == NULL) { - printf ("(EE) VFSListFirst: sDir is NULL!\n"); - return cVFS_Failed; - } printf ("(--) VFSListFirst: Going to list all items in '%s'\n", sDir); - return vfs_filelist_list_first (globs->vfs_filelist, sDir, Item, FollowSymlinks, AddFullPath); + return vfs_filelist_list_first (globs->vfs_filelist, sDir, FollowSymlinks, AddFullPath, error); } -TVFSResult -VFSListNext (struct TVFSGlobs *globs, struct TVFSItem *Item) +struct TVFSItem * +VFSListNext (struct TVFSGlobs *globs, GError **error) { - return vfs_filelist_list_next (globs->vfs_filelist, Item); + return vfs_filelist_list_next (globs->vfs_filelist, error); } -TVFSResult -VFSListClose (struct TVFSGlobs *globs) +gboolean +VFSListClose (struct TVFSGlobs *globs, GError **error) { - return vfs_filelist_list_close (globs->vfs_filelist); + return vfs_filelist_list_close (globs->vfs_filelist, error); } /******************************************************************************************************/ -TVFSResult -VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { printf ("(--) VFSFileInfo: requested info for object '%s'\n", AFileName); - if (! globs) - return cVFS_Failed; - return vfs_filelist_file_info (globs->vfs_filelist, AFileName, Item, FollowSymlinks, AddFullPath); + return vfs_filelist_file_info (globs->vfs_filelist, AFileName, FollowSymlinks, AddFullPath, error); } @@ -608,6 +656,7 @@ VFSBreakGetDirSize (struct TVFSGlobs *globs) /** Methods modifying the archive */ /************** ****************/ +#if 0 TVFSResult VFSMkDir (struct TVFSGlobs *globs, const char *sDirName) { printf ("(WW) VFSMkDir: Not supported in UNRAR plugin.\n"); @@ -649,12 +698,13 @@ TVFSResult VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 m printf ("(WW) VFSChangeTimes: Not supported in UNRAR plugin.\n"); return cVFS_Not_Supported; } - +#endif //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //////////////////////// +#if 0 TVFSFileDes VFSOpenFile(struct TVFSGlobs *globs, const char *APath, int Mode, int *Error) { *Error = cVFS_Not_Supported; @@ -683,6 +733,7 @@ int VFSWriteFile(struct TVFSGlobs *globs, TVFSFileDes FileDescriptor, void *Buff *Error = cVFS_Not_Supported; return 0; } +#endif void VFSSetBlockSize (struct TVFSGlobs *globs, guint32 Value) @@ -710,19 +761,20 @@ VFSTwoSameFiles (struct TVFSGlobs *globs, const char *Path1, const char *Path2, //////////////////////// -TVFSResult -VFSStartCopyOperation (struct TVFSGlobs *globs) +gboolean +VFSStartCopyOperation (struct TVFSGlobs *globs, GError **error) { - TVFSResult Result; struct RAROpenArchiveDataEx *archive_data; HANDLE PASCAL handle; + gboolean Result; - g_return_val_if_fail (globs != NULL, cVFS_Failed); - g_return_val_if_fail (globs->op_handle == NULL, cVFS_Failed); - + if (globs->op_handle != NULL) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_ALREADY_MOUNTED, "globs->op_handle != NULL"); + return FALSE; + } printf ("(II) VFSStartCopyOperation: opening archive '%s'\n", globs->archive_path); - Result = cVFS_Failed; + Result = FALSE; /* WARNING: do not use g_malloc0() here, leads to memory corruption */ archive_data = malloc (sizeof (struct RAROpenArchiveDataEx)); @@ -750,10 +802,11 @@ VFSStartCopyOperation (struct TVFSGlobs *globs) } globs->op_handle = handle; - Result = cVFS_OK; + Result = TRUE; } else { fprintf (stderr, "(EE) VFSStartCopyOperation: error occured when opening archive: OpenResult = %d\n", archive_data->OpenResult); - Result = cVFS_ReadErr; + rar_error_to_gerror (archive_data->OpenResult, error); + Result = FALSE; } free (archive_data); @@ -761,21 +814,25 @@ VFSStartCopyOperation (struct TVFSGlobs *globs) } -TVFSResult -VFSStopCopyOperation (struct TVFSGlobs *globs) +gboolean +VFSStopCopyOperation (struct TVFSGlobs *globs, GError **error) { - TVFSResult Result; int res; - g_return_val_if_fail (globs != NULL, cVFS_Failed); - g_return_val_if_fail (globs->op_handle != NULL, cVFS_Failed); + gboolean Result; + + if (globs->op_handle == NULL) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_ALREADY_MOUNTED, "globs->op_handle == NULL"); + return FALSE; + } printf ("(II) VFSStopCopyOperation: closing archive.\n"); - Result = cVFS_OK; + Result = TRUE; res = RARCloseArchive (globs->op_handle); if (res) { fprintf (stderr, "(EE) VFSCopyToLocal: RARCloseArchive result = %d\n", res); - Result = cVFS_ReadErr; + rar_error_to_gerror (res, error); + Result = FALSE; } globs->op_handle = NULL; @@ -783,19 +840,22 @@ VFSStopCopyOperation (struct TVFSGlobs *globs) } -TVFSResult -VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { struct PathTree *node; - TVFSResult Result; gboolean found; + gboolean Result; char *src; - g_return_val_if_fail (globs->op_handle != NULL, cVFS_ReadErr); - - if (sSrcName == NULL || sDstName == NULL || strlen (sSrcName) < 1 || strlen (sDstName) < 1) { + if (globs->op_handle == NULL) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "globs->op_handle == NULL"); + return FALSE; + } + if (sSrcName == NULL || sDstName == NULL || strlen (sSrcName) < 1 || strlen (sDstName) < 1) { printf ("(EE) VFSCopyToLocal: The value of 'sSrcName' or 'sDstName' is NULL or empty\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "The value of 'sSrcName' or 'sDstName' is NULL or empty."); + return FALSE; } printf ("(II) VFSCopyToLocal: copying file '%s' out to '%s'\n", sSrcName, sDstName); @@ -803,7 +863,8 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN node = filelist_tree_find_node_by_path (globs->files, sSrcName); if (! node) { fprintf (stderr, "(EE) VFSCopyToLocal: cannot find file '%s'\n", sSrcName); - return cVFS_ReadErr; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "cannot find file '%s'", sSrcName); + return FALSE; } src = node->original_pathstr; @@ -820,14 +881,13 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN int res = 0; found = FALSE; - Result = cVFS_OK; + Result = TRUE; while ((res = RARReadHeaderEx(globs->op_handle, header)) == 0) { g_print ("VFSCopyToLocal: found '%s'\n", header->FileName); if (g_strcmp0 (src, header->FileName) == 0) { // fprintf(stderr, "(II) VFSCopyToLocal: extract_file_path(sDstName) = '%s', extract_file_name(sDstName) = '%s' \n", extract_file_path(sDstName), extract_file_name(sDstName)); globs->extract_done = 0; - globs->extract_file_size = (guint64)((guint64)(header->UnpSizeHigh * 0x100000000) + (guint64)header->UnpSize); globs->extract_cancelled = FALSE; found = TRUE; @@ -835,19 +895,22 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN if (globs->extract_cancelled) { fprintf (stderr, "(WW) VFSCopyToLocal: cancelled !\n"); - Result = cVFS_Cancelled; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CANCELLED, "Operation has been cancelled."); + Result = FALSE; } else if (res2) { fprintf (stderr, "(EE) VFSCopyToLocal: RARProcessFile result = %d\n", res2); - Result = cVFS_ReadErr; + rar_error_to_gerror (res2, error); + Result = FALSE; } break; } else { int res2 = RARProcessFile (globs->op_handle, RAR_SKIP, NULL, NULL); if (res2) { fprintf (stderr, "(EE) VFSCopyToLocal: RARProcessFile result = %d\n", res2); - Result = cVFS_ReadErr; + rar_error_to_gerror (res2, error); + Result = FALSE; } } } @@ -856,55 +919,32 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN if (res != ERAR_END_ARCHIVE && res) { if (globs->extract_cancelled) { fprintf (stderr, "(WW) VFSCopyToLocal: cancelled !\n"); - Result = cVFS_Cancelled; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CANCELLED, "Operation has been cancelled."); + Result = FALSE; } else { fprintf (stderr, "(EE) VFSCopyToLocal: RARReadHeader result = %d\n", res); - switch (res) { - case ERAR_NO_MEMORY: - case ERAR_SMALL_BUF: - Result = cVFS_mallocFailed; - break; - case ERAR_BAD_DATA: - case ERAR_BAD_ARCHIVE: - case ERAR_UNKNOWN_FORMAT: - case ERAR_EOPEN: - case ERAR_ECLOSE: - case ERAR_EREAD: - Result = cVFS_ReadErr; - break; - case ERAR_ECREATE: - case ERAR_EWRITE: - Result = cVFS_WriteErr; - break; - case ERAR_MISSING_PASSWORD: - Result = cVFS_BadPassword; - g_free (globs->password); - globs->password = NULL; - break; - case ERAR_UNKNOWN: - default: - Result = cVFS_WriteErr; - break; - } + rar_error_to_gerror (res, error); } } free (header); - if (! found && Result == cVFS_OK) { + if (! found && Result) { fprintf (stderr, "(EE) VFSCopyToLocal: file not found in archive.\n"); - Result = cVFS_ReadErr; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "File not found in archive."); + Result = FALSE; } fprintf (stderr, "(II) VFSCopyToLocal: finished. \n"); return Result; } -TVFSResult -VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { printf ("(WW) VFSCopyFromLocal: Not supported in UNRAR plugin.\n"); - return cVFS_Not_Supported; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, "Not supported in UNRAR plugin."); + return FALSE; } diff --git a/zip/Makefile b/zip/Makefile index eb45047..aeef6f5 100644 --- a/zip/Makefile +++ b/zip/Makefile @@ -23,15 +23,15 @@ VFS_CPP_OBJECTS = zip.o .SUFFIXES: .c .cpp .c.o: - $(CC) $(CFLAGS) `pkg-config glib-2.0 --cflags` -c $< + $(CC) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --cflags` -c $< .cpp.o: - $(CPP) $(CFLAGS) `pkg-config glib-2.0 --cflags` -c $< + $(CPP) $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --cflags` -c $< all shared static: libzip_plugin.so libzip_plugin.so: ziparchive $(VFS_COMMON_OBJECTS) $(VFS_CPP_OBJECTS) $(VFS_C_OBJECTS) - $(CPP) -shared -o libzip_plugin.so zip.o $(VFS_COMMON_OBJECTS) $(DIR_ZIPARCHIVE)libziparch.a -lz -lm $(CFLAGS) `pkg-config glib-2.0 --libs` + $(CPP) -shared -o libzip_plugin.so zip.o $(VFS_COMMON_OBJECTS) $(DIR_ZIPARCHIVE)libziparch.a -lz -lm $(CFLAGS) `pkg-config glib-2.0 gio-2.0 --libs` ziparchive: ( cd $(DIR_ZIPARCHIVE) && make -f ../Makefile.ziparch ) || exit 1 diff --git a/zip/zip.cpp b/zip/zip.cpp index 8e2e1e7..e7dc7ed 100644 --- a/zip/zip.cpp +++ b/zip/zip.cpp @@ -1,5 +1,5 @@ /* ZIP plugin for Tux Commander - * version 0.6.1, designed for ZipArchive v3.2.0 + * version 0.6.2, designed for ZipArchive v3.2.0 * Copyright (C) 2004-2009 Tomas Bzatek <tbzatek@users.sourceforge.net> * Check for updates on tuxcmd.sourceforge.net * @@ -34,6 +34,7 @@ #include <fnmatch.h> #include <unistd.h> #include <glib.h> +#include <gio/gio.h> #include "tuxcmd-vfs.h" #include "strutils.h" @@ -47,59 +48,80 @@ -#define VERSION "0.6.1" -#define BUILD_DATE "2009-11-29" +#define VERSION "0.6.2" +#define BUILD_DATE "2009-12-13" #define DEFAULT_BLOCK_SIZE 65536 using namespace std; extern "C" { + /******************************************************************************************************/ /** Utilities */ /************** ****************/ -static TVFSResult -get_vfs_errorcode (int m_iCause) +static void +zip_error_to_gerror (CZipException e, GError **error) { - switch (m_iCause) { - case 13: return cVFS_WriteErr; // Permission denied - case CZipException::noError: return cVFS_WriteErr; // No error. - case CZipException::genericError: return cVFS_WriteErr; // An unknown error. - case CZipException::badZipFile: return cVFS_ReadErr; // Damaged or not a zip file. - case CZipException::badCrc: return cVFS_ReadErr; // Crc is mismatched. - case CZipException::noCallback: return cVFS_Failed; // There is no spanned archive callback object set. - case CZipException::aborted: return cVFS_Failed; // The disk change callback method returned false. - case CZipException::abortedAction: return cVFS_Failed; // The action callback method returned false. - case CZipException::abortedSafely: return cVFS_Failed; // The action callback method returned false, but the data is not corrupted. - case CZipException::nonRemovable: return cVFS_WriteErr; // The device selected for the spanned archive is not removable. - case CZipException::tooManyVolumes: return cVFS_WriteErr; // The limit of the maximum volumes reached. - case CZipException::tooManyFiles: return cVFS_ReadErr; // The limit of the maximum files in an archive reached. - case CZipException::tooLongData: return cVFS_ReadErr; // The filename, the comment or the local or central extra field of the file added to the archive is too long. - case CZipException::tooBigSize: return cVFS_ReadErr; // The file size is too large to be supported. - case CZipException::badPassword: return cVFS_ReadErr; // An incorrect password set for the file being decrypted. - case CZipException::dirWithSize: return cVFS_ReadErr; // The directory with a non-zero size found while testing. - case CZipException::internalError: return cVFS_WriteErr; // An internal error. - case CZipException::notRemoved: return cVFS_WriteErr; // Error while removing a file - case CZipException::notRenamed: return cVFS_WriteErr; // Error while renaming a file (under Windows call GetLastError() to find out more). - case CZipException::platfNotSupp: return cVFS_WriteErr; // Cannot create a file for the specified platform. - case CZipException::cdirNotFound: return cVFS_ReadErr; // The central directory was not found in the archive (or you were trying to open not the last disk of a segmented archive). + gint code; + + switch (e.m_iCause) { + case CZipException::noError: // No error. + code = G_IO_ERROR_UNKNOWN; + break; + case CZipException::genericError: // An unknown error. + case CZipException::badCrc: // Crc is mismatched. + case CZipException::internalError: // An internal error. + case CZipException::badPassword: // An incorrect password set for the file being decrypted. + case CZipException::dirWithSize: // The directory with a non-zero size found while testing. + case CZipException::streamEnd: // Zlib library error. + case CZipException::needDict: // Zlib library error. + case CZipException::errNo: // Zlib library error. + case CZipException::streamError: // Zlib library error. + case CZipException::dataError: // Zlib library error. + case CZipException::memError: // Zlib library or CZipMemFile error. + case CZipException::bufError: // Zlib library error. + code = G_IO_ERROR_FAILED; + break; + case CZipException::badZipFile: // Damaged or not a zip file. + code = G_IO_ERROR_NOT_MOUNTABLE_FILE; + break; + case CZipException::aborted: // The disk change callback method returned false. + case CZipException::abortedAction: // The action callback method returned false. + case CZipException::abortedSafely: // The action callback method returned false, but the data is not corrupted. + code = G_IO_ERROR_CANCELLED; + break; + case CZipException::nonRemovable: // The device selected for the spanned archive is not removable. + case CZipException::tooManyVolumes: // The limit of the maximum volumes reached. + case CZipException::tooManyFiles: // The limit of the maximum files in an archive reached. + case CZipException::tooLongData: // The filename, the comment or the local or central extra field of the file added to the archive is too long. + case CZipException::tooBigSize: // The file size is too large to be supported. + code = G_IO_ERROR_NOT_SUPPORTED; + break; + + case CZipException::notRemoved: // Error while removing a file + case CZipException::notRenamed: // Error while renaming a file (under Windows call GetLastError() to find out more). + code = G_IO_ERROR_NOT_EMPTY; + break; + case CZipException::cdirNotFound: // The central directory was not found in the archive (or you were trying to open not the last disk of a segmented archive). + code = G_IO_ERROR_NOT_FOUND; + break; // case CZipException::cdir64NotFound: return cVFS_ReadErr; // The Zip64 central directory signature was not found in the archive where expected. // case CZipException::noBBZInZip64: return cVFS_ReadErr; // The number of bytes before a zip archive must be zero in the Zip64 format. // case CZipException::badAesAuthCode: return cVFS_ReadErr; // Mismatched authentication code in WinZip AEC decrypted data. - case CZipException::noZip64: return cVFS_ReadErr; // The Zip64 format has not been enabled for the library, but is required to open the archive. - case CZipException::noAES: return cVFS_ReadErr; // WinZip AES encryption has not been enabled for the library, but is required to decompress the archive. - case CZipException::outOfBounds: return cVFS_ReadErr; // The collection is empty and the bounds do not exist. + case CZipException::platfNotSupp: // Cannot create a file for the specified platform. + case CZipException::noZip64: // The Zip64 format has not been enabled for the library, but is required to open the archive. + case CZipException::noAES: // WinZip AES encryption has not been enabled for the library, but is required to decompress the archive. + code = G_IO_ERROR_NOT_SUPPORTED; + break; + case CZipException::noCallback: // There is no spanned archive callback object set. + case CZipException::outOfBounds: // The collection is empty and the bounds do not exist. + case CZipException::versionError: // Zlib library error. + code = G_IO_ERROR_INVALID_ARGUMENT; + break; // case CZipException::mutexError: return cVFS_ReadErr; // Locking or unlocking resources access was unsuccessful. - case CZipException::streamEnd: return cVFS_ReadErr; // Zlib library error. - case CZipException::needDict: return cVFS_ReadErr; // Zlib library error. - case CZipException::errNo: return cVFS_ReadErr; // Zlib library error. - case CZipException::streamError: return cVFS_ReadErr; // Zlib library error. - case CZipException::dataError: return cVFS_ReadErr; // Zlib library error. - case CZipException::memError: return cVFS_ReadErr; // Zlib library or CZipMemFile error. - case CZipException::bufError: return cVFS_ReadErr; // Zlib library error. - case CZipException::versionError: return cVFS_ReadErr; // Zlib library error. // case CZipException::bzSequenceError: return cVFS_ReadErr; // Bzlib library error. // case CZipException::bzParamError: return cVFS_ReadErr; // Bzlib library error. // case CZipException::bzMemError: return cVFS_ReadErr; // Bzlib library error. @@ -110,8 +132,11 @@ get_vfs_errorcode (int m_iCause) // case CZipException::bzOutbuffFull: return cVFS_ReadErr; // Bzlib library error. // case CZipException::bzConfigError: return cVFS_ReadErr; // Bzlib library error. // case CZipException::bzInternalError: return cVFS_ReadErr; // Internal Bzlib library error. - default: return cVFS_WriteErr; - } + default: + code = G_IO_ERROR_FAILED; + break; + } + g_set_error_literal (error, G_IO_ERROR, code, (LPCTSTR)e.GetErrorDescription()); } @@ -164,7 +189,7 @@ struct ZIP_API CVFSZipActionCallback : public CZipActionCallback bool ret = true; try { if (globs && globs->callback_progress) - ret = globs->callback_progress (m_uProcessed, m_uTotalToProcess, globs->callback_data); + ret = globs->callback_progress (m_uProcessed, NULL, globs->callback_data); } catch (...) { fprintf (stderr, "(EE) extract_callback: Fatal error occured when calling pCallBackProgress\n"); @@ -338,8 +363,8 @@ VFSGetArchiveExts () /**************************************************************************************************************************************/ /**************************************************************************************************************************************/ -TVFSResult -VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) +gboolean +VFSOpenArchive (struct TVFSGlobs *globs, const char *sName, GError **error) { int iCount; @@ -355,7 +380,8 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) try { if (! globs->zip->Open (sName, CZipArchive::zipOpen, 0)) { printf ("(EE) VFSOpenArchive: error opening zip archive\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error opening zip archive."); + return FALSE; } } catch (...) { @@ -364,18 +390,22 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) /* try to open in read only mode (required if there's no write access on the media) */ if (! globs->zip->Open (sName, CZipArchive::zipOpenReadOnly, 0)) { printf ("(EE) VFSOpenArchive: error opening readonly zip archive\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error opening readonly zip archive."); + return FALSE; } } - catch (...) { + catch (CZipException e) { printf ("(EE) VFSOpenArchive: error opening readonly zip\n"); - return cVFS_Failed; + zip_error_to_gerror (e, error); + return FALSE; } } iCount = globs->zip->GetCount (false); printf ("(II) VFSOpenArchive: %i records found, %i files.\n", iCount, globs->zip->GetCount (true)); - if (iCount < 1) - return cVFS_Failed; + if (iCount < 1) { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "No files found in the archive."); + return FALSE; + } /* build global file list */ build_global_filelist (globs); @@ -396,22 +426,24 @@ VFSOpenArchive (struct TVFSGlobs *globs, const char *sName) else printf ("(EE) VFSOpenArchive: Filename in error object: %s\n\n", (LPCTSTR)e.m_szFileName); globs->zip->Close (true); - return cVFS_Failed; + zip_error_to_gerror (e, error); + return FALSE; } catch (...) { printf ("(EE) VFSOpenArchive: Unknown error while processing archive %s\n\n", (LPCTSTR) sName); globs->zip->Close (true); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Unknown error while processing zip archive."); + return FALSE; } globs->archive_path = g_strdup (sName); globs->archive_modified = FALSE; - return cVFS_OK; + return TRUE; } -TVFSResult -VFSClose (struct TVFSGlobs *globs) +gboolean +VFSClose (struct TVFSGlobs *globs, GError **error) { if (globs) { /* close the archive... */ @@ -420,14 +452,15 @@ VFSClose (struct TVFSGlobs *globs) if (globs->archive_modified) globs->zip->Flush (); /* In case of inconsistency, try using afWriteDir value. - * (use when an exception was thrown, yhe Close method writes the + * (use when an exception was thrown, the Close method writes the * central directory structure to the archive, so that the archive should be usable.) */ globs->zip->Close (CZipArchive::afNoException, false); } catch (CZipException e) { fprintf (stderr, "(EE) VFSClose: Error while closing archive: %s\n", (LPCTSTR)e.GetErrorDescription()); - return cVFS_Failed; + zip_error_to_gerror (e, error); + return FALSE; } /* free the ZIP objects... */ @@ -438,7 +471,8 @@ VFSClose (struct TVFSGlobs *globs) } catch (...) { fprintf (stderr, "(EE) VFSClose: Error freeing ZipArchive objects\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error freeing ZipArchive objects."); + return FALSE; } /* free the filelist */ @@ -451,7 +485,7 @@ VFSClose (struct TVFSGlobs *globs) /* free the rest... */ g_free (globs->archive_path); } - return cVFS_OK; + return TRUE; } char * @@ -460,7 +494,7 @@ VFSGetPath (struct TVFSGlobs *globs) return g_strdup (globs->curr_dir); } -TVFSResult +void VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize, gint64 *FSFree, char **FSLabel) { if (FSSize) @@ -469,25 +503,23 @@ VFSGetFileSystemInfo (struct TVFSGlobs *globs, const char *APath, gint64 *FSSize *FSFree = 0; if (FSLabel) *FSLabel = NULL; - return cVFS_OK; } /******************************************************************************************************/ -TVFSResult -VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath) +gboolean +VFSChangeDir (struct TVFSGlobs *globs, const char *NewPath, GError **error) { - if (NewPath == NULL) { - printf ("(EE) VFSChangeDir: NewPath is NULL!\n"); - return cVFS_Failed; - } + char *s; - globs->curr_dir = vfs_filelist_change_dir (globs->vfs_filelist, NewPath); - if (globs->curr_dir) - return cVFS_OK; + s = vfs_filelist_change_dir (globs->vfs_filelist, NewPath, error); + if (s) { + globs->curr_dir = s; + return TRUE; + } else - return cVFS_Failed; + return FALSE; } gboolean @@ -508,40 +540,35 @@ VFSResetPassword (struct TVFSGlobs *globs) /******************************************************************************************************/ -TVFSResult -VFSListFirst (struct TVFSGlobs *globs, const char *sDir, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSListFirst (struct TVFSGlobs *globs, const char *sDir, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { - if (sDir == NULL) { - printf ("(EE) VFSListFirst: sDir is NULL!\n"); - return cVFS_Failed; - } printf ("(--) VFSListFirst: Going to list all items in '%s'\n", sDir); - return vfs_filelist_list_first (globs->vfs_filelist, sDir, Item, FollowSymlinks, AddFullPath); + return vfs_filelist_list_first (globs->vfs_filelist, sDir, FollowSymlinks, AddFullPath, error); } -TVFSResult -VFSListNext (struct TVFSGlobs *globs, struct TVFSItem *Item) +struct TVFSItem * +VFSListNext (struct TVFSGlobs *globs, GError **error) { - return vfs_filelist_list_next (globs->vfs_filelist, Item); + return vfs_filelist_list_next (globs->vfs_filelist, error); } -TVFSResult -VFSListClose (struct TVFSGlobs *globs) +gboolean +VFSListClose (struct TVFSGlobs *globs, GError **error) { - return vfs_filelist_list_close (globs->vfs_filelist); + return vfs_filelist_list_close (globs->vfs_filelist, error); } /******************************************************************************************************/ -TVFSResult -VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, struct TVFSItem *Item, gboolean FollowSymlinks, gboolean AddFullPath) +struct TVFSItem * +VFSFileInfo (struct TVFSGlobs *globs, const char *AFileName, gboolean FollowSymlinks, gboolean AddFullPath, GError **error) { printf ("(--) VFSFileInfo: requested info for object '%s'\n", AFileName); - if (! globs) - return cVFS_Failed; - return vfs_filelist_file_info (globs->vfs_filelist, AFileName, Item, FollowSymlinks, AddFullPath); + + return vfs_filelist_file_info (globs->vfs_filelist, AFileName, FollowSymlinks, AddFullPath, error); } /******************************************************************************************************/ @@ -569,8 +596,8 @@ VFSBreakGetDirSize (struct TVFSGlobs *globs) /** Methods modifying the archive */ /************** ****************/ -TVFSResult -VFSMkDir (struct TVFSGlobs *globs, const char *sDirName) +gboolean +VFSMkDir (struct TVFSGlobs *globs, const char *sDirName, GError **error) { CZipFileHeader header; char *s; @@ -578,11 +605,13 @@ VFSMkDir (struct TVFSGlobs *globs, const char *sDirName) if (sDirName == NULL || strlen (sDirName) < 1) { printf ("(EE) VFSMkDir: The value of 'sDirName' is NULL or empty\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "The value of 'sDirName' is NULL or empty."); + return FALSE; } if (strcmp (sDirName, "/") == 0) { - printf ("(EE) VFSMkDir: Invalid value '%s' (duplicate root entry?)\n", sDirName); - return cVFS_Failed; + printf ("(EE) VFSMkDir: Invalid value '%s' (duplicate the root entry?)\n", sDirName); + g_set_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "Invalid value '%s' (duplicate the root entry?)", sDirName); + return FALSE; } printf ("(II) VFSMkDir: Going to create new directory '%s'...\n", sDirName); @@ -598,29 +627,32 @@ VFSMkDir (struct TVFSGlobs *globs, const char *sDirName) globs->zip->CloseNewFile (); if (! bRet) { printf ("(EE) VFSMkDir: Error creating new directory '%s'\n", sDirName); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error creating new directory."); + return FALSE; } globs->archive_modified = TRUE; build_global_filelist (globs); - return cVFS_OK; + return TRUE; } catch (CZipException e) { globs->zip->CloseNewFile (true); fprintf (stderr, "(EE) VFSMkDir: Error creating new directory '%s': [%d] %s, archive closed = %d.\n", sDirName, e.m_iCause, (LPCTSTR)e.GetErrorDescription(), globs->zip->IsClosed ()); - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } catch (...) { printf ("(EE) VFSMkDir: Error creating new directory '%s'\n", sDirName); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error creating new directory."); + return FALSE; } } -TVFSResult -VFSRemove (struct TVFSGlobs *globs, const char *APath) +gboolean +VFSRemove (struct TVFSGlobs *globs, const char *APath, GError **error) { char *AFile, *AFile1, *AFile2, *AFile3; long int file_no; @@ -634,14 +666,16 @@ VFSRemove (struct TVFSGlobs *globs, const char *APath) if (file_no < 0) { printf ("(EE) VFSRemove: can't find the file specified: '%s'\n", APath); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Can't find the file specified."); + return FALSE; } try { try { if (! globs->zip->RemoveFile (file_no)) { printf ("(EE) VFSRemove: Delete file '%s' failed.\n", APath); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Delete file '%s' failed.", APath); + return FALSE; } build_global_filelist (globs); globs->archive_modified = TRUE; @@ -659,31 +693,33 @@ VFSRemove (struct TVFSGlobs *globs, const char *APath) printf ("(II) VFSRemove: deleted: '%s', parent: '%s', file_no = %ld\n", APath, AFile3, file_no); if (file_no < 0) { printf ("(WW) VFSRemove: sparse ZIP archive detected, adding empty directory: '%s'\n", AFile3); - VFSMkDir (globs, AFile3); + VFSMkDir (globs, AFile3, NULL); } } g_free (AFile1); g_free (AFile2); g_free (AFile3); - return cVFS_OK; + return TRUE; } catch (CZipException e) { fprintf (stderr, "(EE) VFSRemove: Delete file '%s' failed: [%d] %s, archive closed = %d.\n", APath, e.m_iCause, (LPCTSTR)e.GetErrorDescription(), globs->zip->IsClosed ()); - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } catch (...) { printf ("(EE) VFSRemove: Delete file '%s' failed.\n", APath); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Delete file '%s' failed.", APath); + return FALSE; } } -TVFSResult -VFSRename (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName) +gboolean +VFSRename (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, GError **error) { char *AFile; char *ADestFile; @@ -698,44 +734,49 @@ VFSRename (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName) if (file_no < 0) { printf ("(EE) VFSRename: can't find the file specified: '%s'\n", sSrcName); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Can't find the file specified."); + return FALSE; } try { try { if (! globs->zip->RenameFile (file_no, ADestFile)) { printf ("(EE) VFSRename: Rename/move file '%s' failed.\n", sSrcName); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Rename/move file '%s' failed.", sSrcName); + return FALSE; } g_free (ADestFile); build_global_filelist (globs); globs->archive_modified = TRUE; - return cVFS_OK; + return TRUE; } catch (CZipException e) { fprintf (stderr, "(EE) VFSRename: Rename/move file '%s' failed: [%d] %s, archive closed = %d.\n", sSrcName, e.m_iCause, (LPCTSTR)e.GetErrorDescription(), globs->zip->IsClosed ()); - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } catch (...) { printf ("(EE) VFSRename: Rename/move file failed.\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Rename/move file failed."); + return FALSE; } } -TVFSResult -VFSMakeSymLink (struct TVFSGlobs *globs, const char *NewFileName, const char *PointTo) +gboolean +VFSMakeSymLink (struct TVFSGlobs *globs, const char *NewFileName, const char *PointTo, GError **error) { fprintf (stderr, "(EE) VFSMakeSymLink: Symbolic links not supported in ZIP archives.\n"); - return cVFS_Not_Supported; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, "Symbolic links not supported in ZIP archives."); + return FALSE; } -TVFSResult -VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode) +gboolean +VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode, GError **error) { char *AFile; long int file_no; @@ -749,7 +790,8 @@ VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode) if (file_no < 0) { printf ("(EE) VFSChmod: can't find the file specified: '%s'\n", FileName); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Can't find the file specified."); + return FALSE; } try { @@ -764,7 +806,8 @@ VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode) header = globs->zip->GetFileInfo (file_no); if (! header) { printf ("(EE) VFSChmod: Permissions modification of the file '%s' failed: NULL returned by GetFileInfo()\n", FileName); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Permissions modification of the file '%s' failed: NULL returned by GetFileInfo()", FileName); + return FALSE; } // We need to change only 0xF000FFFF mask // The 0xF_______ bits represents file/directory type, the 0x____FFFF represents ZIP attributes and 0x_FFF____ represents unix permissions @@ -795,33 +838,36 @@ VFSChmod (struct TVFSGlobs *globs, const char *FileName, guint32 Mode) printf ("(II) VFSChmod OK.\n"); build_global_filelist (globs); globs->archive_modified = TRUE; - return cVFS_OK; + return TRUE; } catch (CZipException e) { globs->zip->CloseNewFile (true); fprintf (stderr, "(EE) VFSChmod: permissions modification of the file '%s' failed: [%d] %s, archive closed = %d.\n", FileName, e.m_iCause, (LPCTSTR)e.GetErrorDescription(), globs->zip->IsClosed()); - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } catch (...) { printf ("(EE) VFSChmod: permissions modification of the file '%s' failed.\n", FileName); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Permissions modification of the file '%s' failed.", FileName); + return FALSE; } } -TVFSResult -VFSChown (struct TVFSGlobs *globs, const char *FileName, guint32 UID, guint32 GID) +gboolean +VFSChown (struct TVFSGlobs *globs, const char *FileName, guint32 UID, guint32 GID, GError **error) { fprintf (stderr, "(EE) VFSChown: Owner changing is not supported in ZIP archives.\n"); - return cVFS_Not_Supported; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, "Owner changing is not supported in ZIP archives."); + return FALSE; } -TVFSResult -VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint32 atime) +gboolean +VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint32 atime, GError **error) { char *AFile; long int file_no; @@ -835,7 +881,8 @@ VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint if (file_no < 0) { printf ("(EE) VFSChangeTimes: can't find the file specified: '%s'\n", APath); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "Can't find the file specified."); + return FALSE; } try { @@ -845,7 +892,8 @@ VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint header = globs->zip->GetFileInfo (file_no); if (! header) { printf ("(EE) VFSChangeTimes: DateTime modification of the file '%s' failed: NULL returned by GetFileInfo()\n", APath); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "DateTime modification of the file '%s' failed: NULL returned by GetFileInfo()", APath); + return FALSE; } /* change the header data */ header->SetTime (mtime); @@ -864,18 +912,20 @@ VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint printf ("(II) VFSChangeTimes OK.\n"); build_global_filelist (globs); globs->archive_modified = TRUE; - return cVFS_OK; + return TRUE; } catch (CZipException e) { globs->zip->CloseNewFile (true); fprintf (stderr, "(EE) VFSChangeTimes: DateTime modification of the file '%s' failed: [%d] %s, archive closed = %d.\n", APath, e.m_iCause, (LPCTSTR)e.GetErrorDescription (), globs->zip->IsClosed ()); - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } catch (...) { printf ("(EE) VFSChangeTimes: DateTime modification of the file '%s' failed.\n", APath); - return cVFS_Failed; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "DateTime modification of the file '%s' failed.", APath); + return FALSE; } } @@ -884,6 +934,7 @@ VFSChangeTimes (struct TVFSGlobs *globs, const char *APath, guint32 mtime, guint //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //////////////////////// +#if 0 TVFSFileDes VFSOpenFile(struct TVFSGlobs *globs, const char *APath, int Mode, int *Error) { *Error = cVFS_Not_Supported; @@ -912,6 +963,7 @@ int VFSWriteFile(struct TVFSGlobs *globs, TVFSFileDes FileDescriptor, void *Buff *Error = cVFS_Not_Supported; return 0; } +#endif void VFSSetBlockSize (struct TVFSGlobs *globs, guint32 Value) @@ -939,26 +991,21 @@ VFSTwoSameFiles (struct TVFSGlobs *globs, const char *Path1, const char *Path2, //////////////////////// -TVFSResult -VFSStartCopyOperation (struct TVFSGlobs *globs) +gboolean +VFSStartCopyOperation (struct TVFSGlobs *globs, GError **error) { - TVFSResult Result; - - g_return_val_if_fail (globs != NULL, cVFS_Failed); + g_return_val_if_fail (globs != NULL, FALSE); printf ("(II) VFSStartCopyOperation: doing nothing for the moment.\n"); - Result = cVFS_OK; - return Result; + return TRUE; } -TVFSResult -VFSStopCopyOperation (struct TVFSGlobs *globs) +gboolean +VFSStopCopyOperation (struct TVFSGlobs *globs, GError **error) { - TVFSResult Result; - - g_return_val_if_fail (globs != NULL, cVFS_Failed); + g_return_val_if_fail (globs != NULL, FALSE); if (globs->archive_modified) { printf ("(II) VFSStopCopyOperation: rebuilding tree.\n"); @@ -967,9 +1014,8 @@ VFSStopCopyOperation (struct TVFSGlobs *globs) } else { printf ("(II) VFSStartCopyOperation: doing nothing for the moment.\n"); } - Result = cVFS_OK; - return Result; + return TRUE; } @@ -977,8 +1023,8 @@ VFSStopCopyOperation (struct TVFSGlobs *globs) * - crashes when no space left on NFS mounts, probably unhandled exception in further ZipArchive code (repro: Gentoo, Ubuntu) * **/ -TVFSResult -VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { gboolean try_again; long int file_no; @@ -991,7 +1037,8 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN if (sSrcName == NULL || sDstName == NULL || strlen (sSrcName) < 1 || strlen (sDstName) < 1) { printf ("(EE) VFSCopyToLocal: The value of 'sSrcName' or 'sDstName' is NULL or empty\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "The value of 'sSrcName' or 'sDstName' is NULL or empty."); + return FALSE; } printf ("(II) VFSCopyToLocal: copying file '%s' out to '%s'\n", sSrcName, sDstName); @@ -999,7 +1046,8 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN file_no = filelist_find_original_index_by_path (globs->files, sSrcName) - 1; if (file_no < 0) { printf ("(EE) VFSCopyToLocal: can't find source file '%s'\n", sSrcName); - return cVFS_ReadErr; + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "cannot find file '%s'", sSrcName); + return FALSE; } s = exclude_trailing_path_sep (sDstName); @@ -1015,7 +1063,8 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN if (! globs->zip->ExtractFile (file_no, dest_path, false, dest_filename, globs->block_size)) { globs->zip->CloseFile (NULL, true); fprintf (stderr, "(EE) VFSCopyToLocal: Error while copying out, archive closed = %d.\n", globs->zip->IsClosed ()); - return cVFS_WriteErr; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error while copying out."); + return FALSE; } fprintf (stderr, "(II) VFSCopyToLocal: copy OK, archive closed = %d.\n", globs->zip->IsClosed ()); } @@ -1036,11 +1085,14 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN globs->zip->SetPassword (passwd); try_again = TRUE; break; - } else - return cVFS_Cancelled; + } else { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CANCELLED, "Operation has been cancelled."); + return FALSE; + } } default: - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } } while (try_again); @@ -1048,12 +1100,13 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN catch (...) { fprintf (stderr, "(EE) VFSCopyToLocal: Fatal error while copying out..., archive closed = %d.\n", globs->zip->IsClosed()); - return cVFS_WriteErr; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Fatal error while copying out."); + return FALSE; } g_free (dest_path); g_free (dest_filename); - return cVFS_OK; + return TRUE; } @@ -1062,8 +1115,8 @@ VFSCopyToLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstN * - encrypted files are unreadable after copy in * **/ -TVFSResult -VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append) +gboolean +VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDstName, gboolean Append, GError **error) { gboolean try_again; char *s; @@ -1072,7 +1125,8 @@ VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDs if (sSrcName == NULL || sDstName == NULL || strlen (sSrcName) < 1 || strlen (sDstName) < 1) { printf ("(EE) VFSCopyFromLocal: The value of 'sSrcName' or 'sDstName' is NULL or empty\n"); - return cVFS_Failed; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT, "The value of 'sSrcName' or 'sDstName' is NULL or empty."); + return FALSE; } printf ("(II) VFSCopyFromLocal: copying file '%s' in to '%s'\n", sSrcName, sDstName); @@ -1086,7 +1140,8 @@ VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDs globs->zip->CloseNewFile (true); globs->zip->CloseFile (NULL, true); fprintf (stderr, "(EE) VFSCopyFromLocal: Error while copying in, archive closed = %d.\n", globs->zip->IsClosed ()); - return cVFS_WriteErr; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Error while copying in."); + return FALSE; } printf ("(II) VFSCopyFromLocal: copy OK, archive closed = %d.\n", globs->zip->IsClosed ()); @@ -1126,21 +1181,25 @@ VFSCopyFromLocal (struct TVFSGlobs *globs, const char *sSrcName, const char *sDs globs->zip->SetPassword (passwd); try_again = TRUE; break; - } else - return cVFS_Cancelled; + } else { + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CANCELLED, "Operation has been cancelled."); + return FALSE; + } } default: - return get_vfs_errorcode (e.m_iCause); + zip_error_to_gerror (e, error); + return FALSE; } } } while (try_again); } catch (...) { fprintf (stderr, "(EE) VFSCopyFromLocal: Fatal error while copying in..., archive closed = %d.\n", globs->zip->IsClosed()); - return cVFS_WriteErr; + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Fatal error while copying in."); + return FALSE; } - return cVFS_OK; + return TRUE; } |
