diff options
| -rw-r--r-- | src/dlg-prop.c | 10 | ||||
| -rw-r--r-- | src/fr-command-rar.c | 70 | ||||
| -rw-r--r-- | src/fr-command-rar.h | 8 | ||||
| -rw-r--r-- | src/fr-window.c | 16 |
4 files changed, 70 insertions, 34 deletions
diff --git a/src/dlg-prop.c b/src/dlg-prop.c index cb8ed87..e82d5f1 100644 --- a/src/dlg-prop.c +++ b/src/dlg-prop.c @@ -101,10 +101,12 @@ dlg_prop (FrWindow *window) GDateTime *date_time; date_time = g_date_time_new_from_unix_local (get_file_mtime (fr_window_get_archive_uri (window))); - s = g_date_time_format (date_time, _("%d %B %Y, %H:%M")); - g_date_time_unref (date_time); - gtk_label_set_text (GET_LABEL ("p_date_label"), s); - g_free (s); + if (date_time) { + s = g_date_time_format (date_time, _("%d %B %Y, %H:%M")); + g_date_time_unref (date_time); + gtk_label_set_text (GET_LABEL ("p_date_label"), s); + g_free (s); + } /**/ diff --git a/src/fr-command-rar.c b/src/fr-command-rar.c index 956b88f..880bfe9 100644 --- a/src/fr-command-rar.c +++ b/src/fr-command-rar.c @@ -39,6 +39,10 @@ #include "fr-error.h" #include "rar-utils.h" + +#define IS_OUTPUT_TYPE(comm, type) ((comm)->output_type & (type)) + + static void fr_command_rar_class_init (FrCommandRarClass *class); static void fr_command_rar_init (FrCommand *afile); static void fr_command_rar_finalize (GObject *object); @@ -150,6 +154,18 @@ attribute_field_with_space (const char *line) return ((line[0] != ' ') && (line[1] == ' ')); } +static gboolean +attr_field_is_dir (const char *attr_field, + FrCommandRar *rar_comm) +{ + if ((attr_field[0] == 'd') || + (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5) && attr_field[3] == 'D') || + (! IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5) && attr_field[1] == 'D')) + return TRUE; + + return FALSE; +} + static void parse_name_field (char *line, FrCommandRar *rar_comm) @@ -163,9 +179,19 @@ parse_name_field (char *line, fdata->encrypted = (line[0] == '*') ? TRUE : FALSE; - if (rar_comm->output_type == FR_COMMAND_RAR_TYPE_RAR5) { - const char *field = get_last_field (line, attribute_field_with_space (line) ? 9 : 8); + if (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5)) { + int field_num = attribute_field_with_space (line) ? 9 : 8; + const char *field; + /* in RAR7 format, directories have a blank CRC32, not the + * "????????" of the RAR5 format */ + if (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR7)) { + field = get_last_field (line, field_num - 8); + if (attr_field_is_dir (field, rar_comm)) + field_num--; + } + + field = get_last_field (line, field_num); /* rar-5 output adds trailing spaces to short file names :( */ name_field = field ? g_strchomp (g_strdup (field)) : NULL; } else @@ -189,18 +215,6 @@ parse_name_field (char *line, g_free (name_field); } -static gboolean -attr_field_is_dir (const char *attr_field, - FrCommandRar *rar_comm) -{ - if ((attr_field[0] == 'd') || - (rar_comm->output_type == FR_COMMAND_RAR_TYPE_RAR5 && attr_field[3] == 'D') || - (rar_comm->output_type != FR_COMMAND_RAR_TYPE_RAR5 && attr_field[1] == 'D')) - return TRUE; - - return FALSE; -} - static void process_line (char *line, gpointer data) @@ -215,7 +229,12 @@ process_line (char *line, int version = 0; if (sscanf (line, "RAR %d.", &version) == 1 || sscanf (line, "UNRAR %d.", &version) == 1) { - rar_comm->output_type = (version >= 5) ? FR_COMMAND_RAR_TYPE_RAR5 : FR_COMMAND_RAR_TYPE_RAR4; + if (version >= 7) + rar_comm->output_type = FR_COMMAND_RAR_TYPE_RAR7; + else if (version >= 5) + rar_comm->output_type = FR_COMMAND_RAR_TYPE_RAR5; + else + rar_comm->output_type = FR_COMMAND_RAR_TYPE_RAR4; if (version > 5) date_newstyle = TRUE; @@ -232,7 +251,7 @@ process_line (char *line, } else if (strncmp (line, "--------", 8) == 0) { rar_comm->list_started = TRUE; - if (rar_comm->output_type != FR_COMMAND_RAR_TYPE_RAR5) + if (! IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5)) rar_comm->rar4_odd_line = TRUE; } else if (strncmp (line, "Volume ", 7) == 0) @@ -245,7 +264,7 @@ process_line (char *line, return; } - if (rar_comm->rar4_odd_line || rar_comm->output_type == FR_COMMAND_RAR_TYPE_RAR5) + if (rar_comm->rar4_odd_line || IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5)) parse_name_field (line, rar_comm); if (! rar_comm->rar4_odd_line && rar_comm->fdata && rar_comm->fdata->full_path) { @@ -253,9 +272,9 @@ process_line (char *line, const char *size_field, *ratio_field, *date_field, *time_field, *attr_field; int n_fields; - if (rar_comm->output_type == FR_COMMAND_RAR_TYPE_RAR5) + if (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5)) n_fields = 6 + (attribute_field_with_space (line) != 0); - else if (rar_comm->output_type == FR_COMMAND_RAR_TYPE_UNRAR_FREE) + else if (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_UNRAR_FREE)) n_fields = 4; else n_fields = 6; @@ -274,7 +293,7 @@ process_line (char *line, parse_name_field (line, rar_comm); } else { - if (rar_comm->output_type == FR_COMMAND_RAR_TYPE_RAR5) { + if (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5)) { int offset = attribute_field_with_space (line) ? 1 : 0; size_field = fields[1+offset]; @@ -283,7 +302,7 @@ process_line (char *line, time_field = fields[5+offset]; attr_field = fields[0+offset]; } - else if (rar_comm->output_type == FR_COMMAND_RAR_TYPE_UNRAR_FREE) { + else if (IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_UNRAR_FREE)) { size_field = fields[0]; date_field = fields[1]; time_field = fields[2]; @@ -338,7 +357,7 @@ process_line (char *line, } } - if (rar_comm->output_type != FR_COMMAND_RAR_TYPE_RAR5) + if (! IS_OUTPUT_TYPE (rar_comm, FR_COMMAND_RAR_TYPE_RAR5)) rar_comm->rar4_odd_line = ! rar_comm->rar4_odd_line; } @@ -678,7 +697,12 @@ fr_command_rar_handle_error (FrCommand *comm, volume_filename = g_path_get_basename (line + strlen ("Cannot find volume ")); error->gerror = g_error_new (FR_ERROR, error->status, _("Could not find the volume: %s"), volume_filename); g_free (volume_filename); - break; + + /* RAR7 complains about missing volume for incorrect passwords + * as well, so don't make this a definite error in case we also + * had an incorrect password one earlier */ + if (! IS_OUTPUT_TYPE (FR_COMMAND_RAR (comm), FR_COMMAND_RAR_TYPE_RAR7)) + break; } } } diff --git a/src/fr-command-rar.h b/src/fr-command-rar.h index 185d24e..ab4e12d 100644 --- a/src/fr-command-rar.h +++ b/src/fr-command-rar.h @@ -40,9 +40,11 @@ typedef struct _FrCommandRarClass FrCommandRarClass; typedef enum { - FR_COMMAND_RAR_TYPE_RAR4 = 0, - FR_COMMAND_RAR_TYPE_RAR5, - FR_COMMAND_RAR_TYPE_UNRAR_FREE, + FR_COMMAND_RAR_TYPE_RAR4 = 1<<0, + FR_COMMAND_RAR_TYPE_RAR5 = 1<<1, + FR_COMMAND_RAR_TYPE_UNRAR_FREE = 1<<2, + /* RAR5 + empty CRC for directories */ + FR_COMMAND_RAR_TYPE_RAR7 = (1<<3) | FR_COMMAND_RAR_TYPE_RAR5, } FrCommandRarType; struct _FrCommandRar diff --git a/src/fr-window.c b/src/fr-window.c index e86f7e0..d1ce30c 100644 --- a/src/fr-window.c +++ b/src/fr-window.c @@ -1493,8 +1493,12 @@ fr_window_populate_file_list (FrWindow *window, } else { GDateTime *date_time; date_time = g_date_time_new_from_unix_local (fdata->modified); - s_time = g_date_time_format (date_time, _("%d %B %Y, %H:%M")); - g_date_time_unref (date_time); + if (! date_time) { + s_time = g_strdup (""); + } else { + s_time = g_date_time_format (date_time, _("%d %B %Y, %H:%M")); + g_date_time_unref (date_time); + } } gtk_list_store_set (window->priv->list_store, &iter, @@ -1522,8 +1526,12 @@ fr_window_populate_file_list (FrWindow *window, s_size = g_format_size (fdata->size); date_time = g_date_time_new_from_unix_local (fdata->modified); - s_time = g_date_time_format (date_time, _("%d %B %Y, %H:%M")); - g_date_time_unref (date_time); + if (! date_time) { + s_time = g_strdup(""); + } else { + s_time = g_date_time_format (date_time, _("%d %B %Y, %H:%M")); + g_date_time_unref (date_time); + } desc = g_content_type_get_description (fdata->content_type); gtk_list_store_set (window->priv->list_store, &iter, |
