/*
* Geeqie
* (C) 2005 John Ellis
+ * Copyright (C) 2008 The Geeqie Team
*
* Author: John Ellis
*
*/
-#include "gqview.h"
+#include "main.h"
#include "dupe.h"
#include "cache.h"
#include "collect-table.h"
#include "dnd.h"
#include "editors.h"
-#include "filelist.h"
+#include "filedata.h"
#include "image-load.h"
#include "img-view.h"
#include "info.h"
#include "layout_image.h"
#include "md5-util.h"
#include "menu.h"
+#include "misc.h"
#include "print.h"
#include "thumb.h"
-#include "utilops.h"
-#include "ui_bookmark.h"
#include "ui_fileops.h"
#include "ui_menu.h"
#include "ui_misc.h"
#include "ui_tree_edit.h"
+#include "uri_utils.h"
+#include "utilops.h"
+#include "window.h"
#include <gdk/gdkkeysyms.h> /* for keyboard values */
#include <math.h>
-#define DUPE_DEF_WIDTH 600
+#define DUPE_DEF_WIDTH 800
#define DUPE_DEF_HEIGHT 400
/* column assignment order (simply change them here) */
static void dupe_dnd_init(DupeWindow *dw);
+static void dupe_notify_cb(FileData *fd, NotifyType type, gpointer data);
+
/*
* ------------------------------------------------------------------
* Window updates
{
new_time = msec_time() - dw->setup_time;
}
-
+
if (!force &&
value != 0.0 &&
dw->setup_count > 0 &&
{
status_text = NULL;
}
- }
+ }
else
{
gtk_progress_bar_set_fraction(GTK_PROGRESS_BAR(dw->extra_label), 0.0);
GdkCursor *cursor;
if (!widget->window) return;
-
+
if (icon == -1)
{
cursor = NULL;
}
else
{
- cursor = gdk_cursor_new (icon);
+ cursor = gdk_cursor_new(icon);
}
-
+
gdk_window_set_cursor(widget->window, cursor);
-
+
if (cursor) gdk_cursor_unref(cursor);
}
if (!di) return;
base = cache_get_location(CACHE_TYPE_SIM, di->fd->path, FALSE, &mode);
- if (cache_ensure_dir_exists(base, mode))
+ if (recursive_mkdir_if_not_exists(base, mode))
{
CacheData *cd;
else
{
rank = 1;
- printf("NULL group in item!\n");
+ log_printf("NULL group in item!\n");
}
}
else
static void dupe_match_link_clear(DupeItem *parent, gint unlink_children)
{
GList *work;
-
+
work = parent->group;
while (work)
{
{
GList *work;
- printf("+ %f %s\n", di->group_rank, di->fd->name);
+ log_printf("+ %f %s\n", di->group_rank, di->fd->name);
work = di->group;
while (work)
DupeMatch *dm = work->data;
work = work->next;
- printf(" %f %s\n", dm->rank, dm->di->fd->name);
+ log_printf(" %f %s\n", dm->rank, dm->di->fd->name);
}
- printf("\n");
+ log_printf("\n");
}
static void dupe_match_print_list(GList *list)
GList *work;
gdouble rank;
- if (debug > 1) printf("link found %s to %s [%d]\n", child->fd->name, parent->fd->name, g_list_length(parent->group));
+ DEBUG_2("link found %s to %s [%d]", child->fd->name, parent->fd->name, g_list_length(parent->group));
work = parent->group;
while (work)
list = g_list_remove(list, orphan);
}
}
-
+
rank = dupe_match_link_rank(child, parent);
dupe_match_link_clear(parent, TRUE);
dupe_match_link(child, parent, rank);
}
else
{
- if (debug > 1) printf("unlinking %s and %s\n", child->fd->name, parent->fd->name);
-
+ DEBUG_2("unlinking %s and %s", child->fd->name, parent->fd->name);
+
dupe_match_unlink(child, parent);
}
dupe_match_rank_update(di);
list = g_list_prepend(list, di);
}
-
+
work = work->next;
}
list = dupe_match_rank_sort(dw->list);
- if (debug > 1) dupe_match_print_list(list);
-
- if (debug) printf("Similar items: %d\n", g_list_length(list));
+ if (required_debug_level(2)) dupe_match_print_list(list);
+
+ DEBUG_1("Similar items: %d", g_list_length(list));
list = dupe_match_group_trim(list, dw);
- if (debug) printf("Unique groups: %d\n", g_list_length(list));
+ DEBUG_1("Unique groups: %d", g_list_length(list));
dupe_match_sort_groups(list);
- if (debug) dupe_match_print_list(list);
+ if (required_debug_level(2)) dupe_match_print_list(list);
list = dupe_match_rank_sort(list);
if (mask & DUPE_MATCH_PATH)
{
- if (strcmp(a->fd->path, b->fd->path) != 0) return FALSE;
+ if (utf8_compare(a->fd->path, b->fd->path, TRUE) != 0) return FALSE;
}
if (mask & DUPE_MATCH_NAME)
{
- if (strcmp(a->fd->name, b->fd->name) != 0) return FALSE;
+ if (strcmp(a->fd->collate_key_name, b->fd->collate_key_name) != 0) return FALSE;
}
if (mask & DUPE_MATCH_NAME_CI)
{
- if (strcasecmp(a->fd->name, b->fd->name) != 0) return FALSE;
+ if (strcmp(a->fd->collate_key_name_nocase, b->fd->collate_key_name_nocase) != 0) return FALSE;
}
if (mask & DUPE_MATCH_SIZE)
{
if (mask & DUPE_MATCH_SIM_HIGH) m = 0.95;
else if (mask & DUPE_MATCH_SIM_MED) m = 0.90;
- else if (mask & DUPE_MATCH_SIM_CUSTOM) m = (gdouble)dupe_custom_threshold / 100.0;
+ else if (mask & DUPE_MATCH_SIM_CUSTOM) m = (gdouble)options->duplicates_similarity_threshold / 100.0;
else m = 0.85;
if (fast)
if (f < m) return FALSE;
- if (debug > 2) printf("similar: %32s %32s = %f\n", a->fd->name, b->fd->name, f);
+ DEBUG_3("similar: %32s %32s = %f", a->fd->name, b->fd->name, f);
}
return TRUE;
di = dw->thumb_item;
if (di->pixbuf) g_object_unref(di->pixbuf);
- di->pixbuf = thumb_loader_get_pixbuf(dw->thumb_loader, TRUE);
+ di->pixbuf = thumb_loader_get_pixbuf(dw->thumb_loader);
dupe_listview_set_thumb(dw, di, NULL);
}
dw->thumb_item = di;
thumb_loader_free(dw->thumb_loader);
- dw->thumb_loader = thumb_loader_new(thumb_max_width, thumb_max_height);
+ dw->thumb_loader = thumb_loader_new(options->thumbnails.max_width, options->thumbnails.max_height);
thumb_loader_set_callbacks(dw->thumb_loader,
dupe_thumb_done_cb,
dw);
/* start it */
- if (!thumb_loader_start(dw->thumb_loader, di->fd->path))
+ if (!thumb_loader_start(dw->thumb_loader, di->fd))
{
/* error, handle it, do next */
- if (debug) printf("error loading thumb for %s\n", di->fd->path);
+ DEBUG_1("error loading thumb for %s", di->fd->path);
dupe_thumb_do(dw);
dupe_thumb_step(dw);
}
di->width = gdk_pixbuf_get_width(pixbuf);
di->height = gdk_pixbuf_get_height(pixbuf);
}
- if (enable_thumb_caching)
+ if (options->thumbnails.enable_caching)
{
dupe_item_write_cache(di);
}
dupe_window_update_progress(dw, _("Reading checksums..."),
dw->setup_count == 0 ? 0.0 : (gdouble)(dw->setup_n - 1) / dw->setup_count, FALSE);
- if (enable_thumb_caching)
+ if (options->thumbnails.enable_caching)
{
dupe_item_read_cache(di);
if (di->md5sum) return TRUE;
}
di->md5sum = md5_text_from_file_utf8(di->fd->path, "");
- if (enable_thumb_caching)
+ if (options->thumbnails.enable_caching)
{
dupe_item_write_cache(di);
}
dupe_window_update_progress(dw, _("Reading dimensions..."),
dw->setup_count == 0 ? 0.0 : (gdouble)(dw->setup_n - 1) / dw->setup_count, FALSE);
- if (enable_thumb_caching)
+ if (options->thumbnails.enable_caching)
{
dupe_item_read_cache(di);
if (di->width != 0 || di->height != 0) return TRUE;
}
image_load_dimensions(di->fd, &di->width, &di->height);
- if (enable_thumb_caching)
+ if (options->thumbnails.enable_caching)
{
dupe_item_write_cache(di);
}
dupe_window_update_progress(dw, _("Reading similarity data..."),
dw->setup_count == 0 ? 0.0 : (gdouble)dw->setup_n / dw->setup_count, FALSE);
- if (enable_thumb_caching)
+ if (options->thumbnails.enable_caching)
{
dupe_item_read_cache(di);
if (cache_sim_data_filled(di->simd))
dw->img_loader = image_loader_new(di->fd);
image_loader_set_buffer_size(dw->img_loader, 8);
- image_loader_set_error_func(dw->img_loader, dupe_loader_done_cb, dw);
+ g_signal_connect (G_OBJECT(dw->img_loader), "error", (GCallback)dupe_loader_done_cb, dw);
+ g_signal_connect (G_OBJECT(dw->img_loader), "done", (GCallback)dupe_loader_done_cb, dw);
- if (!image_loader_start(dw->img_loader, dupe_loader_done_cb, dw))
+ if (!image_loader_start(dw->img_loader))
{
image_sim_free(di->simd);
di->simd = image_sim_new();
{
DupeItem *new_parent;
DupeMatch *dm;
-
+
dm = parent->group->data;
new_parent = dm->di;
dupe_match_reparent(dw, parent, new_parent);
else if (isdir(fd->path) && recurse)
{
GList *f, *d;
- if (filelist_read(fd->path, &f, &d))
+ if (filelist_read(fd, &f, &d))
{
GList *work;
d = filelist_filter(d, TRUE);
work = f;
- while(work)
+ while (work)
{
dupe_files_add(dw, NULL, NULL, (FileData *)work->data, TRUE);
work = work->next;
}
filelist_free(f);
work = d;
- while(work)
+ while (work)
{
dupe_files_add(dw, NULL, NULL, (FileData *)work->data, TRUE);
work = work->next;
CollectInfo *info;
info = collection_get_first(collection);
- while(info)
+ while (info)
{
dupe_files_add(dw, collection, info, NULL, FALSE);
info = collection_next_by_info(collection, info);
GList *work;
work = list;
- while(work)
+ while (work)
{
FileData *fd = work->data;
work = work->next;
dw->second_drop = second;
dupe_files_add(dw, NULL, NULL, fd, FALSE);
dw->second_drop = FALSE;
-
+
file_data_unref(fd);
*/
dupe_check_start(dw);
{
DupeItem *di = work->data;
- if (di->fd == fd)
+ if (di->fd == fd)
dupe_item_update(dw, di);
work = work->next;
label = gtk_label_new(text);
gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
gtk_widget_show(label);
-
+
gtk_box_pack_start(GTK_BOX(vbox), hbox, FALSE, FALSE, 0);
gtk_widget_show(hbox);
{
GenericDialog *gd;
gchar *buf;
-
+
if (!di) return;
- gd = file_util_gen_dlg("Image thumbprint debug info", GQ_WMCLASS, "thumbprint",
+ gd = file_util_gen_dlg("Image thumbprint debug info", "thumbprint",
dw->window, TRUE,
NULL, NULL);
generic_dialog_add_button(gd, GTK_STOCK_CLOSE, NULL, NULL, TRUE);
guchar *dp;
gint rs;
gint sp;
-
+
pixbuf = gdk_pixbuf_new(GDK_COLORSPACE_RGB, FALSE, 8, 32, 32);
rs = gdk_pixbuf_get_rowstride(pixbuf);
d_pix = gdk_pixbuf_get_pixels(pixbuf);
image = gtk_image_new_from_pixbuf(pixbuf);
gtk_box_pack_start(GTK_BOX(gd->vbox), image, FALSE, FALSE, 0);
gtk_widget_show(image);
-
- gdk_pixbuf_unref(pixbuf);
+
+ g_object_unref(pixbuf);
}
-
+
gtk_widget_show(gd->dialog);
}
dupe_listview_realign_colors(dw);
}
-static void dupe_window_edit_selected(DupeWindow *dw, gint n)
+static void dupe_window_edit_selected(DupeWindow *dw, const gchar *key)
{
GList *list;
list = dupe_listview_get_selection(dw, dw->listview);
- start_editor_from_filelist(n, list);
+ file_util_start_editor_from_filelist(key, list, dw->window);
filelist_free(list);
}
static void dupe_menu_edit_cb(GtkWidget *widget, gpointer data)
{
DupeWindow *dw;
- gint n;
+ const gchar *key = data;
dw = submenu_item_get_data(widget);
- n = GPOINTER_TO_INT(data);
if (!dw) return;
- dupe_window_edit_selected(dw, n);
+ dupe_window_edit_selected(dw, key);
}
static void dupe_menu_info_cb(GtkWidget *widget, gpointer data)
{
DupeWindow *dw = data;
- info_window_new(NULL, dupe_listview_get_selection(dw, dw->listview));
+ info_window_new(NULL, dupe_listview_get_selection(dw, dw->listview), NULL);
}
static void dupe_menu_collection_cb(GtkWidget *widget, gpointer data)
file_util_delete(NULL, dupe_listview_get_selection(dw, dw->listview), dw->window);
}
+static void dupe_menu_copy_path_cb(GtkWidget *widget, gpointer data)
+{
+ DupeWindow *dw = data;
+
+ file_util_copy_path_list_to_clipboard(dupe_listview_get_selection(dw, dw->listview));
+}
+
static void dupe_menu_remove_cb(GtkWidget *widget, gpointer data)
{
DupeWindow *dw = data;
G_CALLBACK(dupe_menu_rename_cb), dw);
menu_item_add_stock_sensitive(menu, _("_Delete..."), GTK_STOCK_DELETE, on_row,
G_CALLBACK(dupe_menu_delete_cb), dw);
+ if (options->show_copy_path)
+ menu_item_add_sensitive(menu, _("_Copy path"), on_row,
+ G_CALLBACK(dupe_menu_copy_path_cb), dw);
menu_item_add_divider(menu);
menu_item_add_stock_sensitive(menu, _("Rem_ove"), GTK_STOCK_REMOVE, on_row,
G_CALLBACK(dupe_menu_remove_cb), dw);
dw->click_item = di;
- if (bevent->button == 3)
+ if (bevent->button == MOUSE_BUTTON_RIGHT)
{
/* right click menu */
GtkWidget *menu;
if (!di) return FALSE;
- if (bevent->button == 1 && bevent->type == GDK_2BUTTON_PRESS)
+ if (bevent->button == MOUSE_BUTTON_LEFT &&
+ bevent->type == GDK_2BUTTON_PRESS)
{
dupe_menu_view(dw, di, widget, FALSE);
}
- if (bevent->button == 2) return TRUE;
+ if (bevent->button == MOUSE_BUTTON_MIDDLE) return TRUE;
- if (bevent->button == 3)
+ if (bevent->button == MOUSE_BUTTON_RIGHT)
{
if (!dupe_listview_item_is_selected(dw, di, widget))
{
return TRUE;
}
- if (bevent->button == 1 && bevent->type == GDK_BUTTON_PRESS &&
+ if (bevent->button == MOUSE_BUTTON_LEFT &&
+ bevent->type == GDK_BUTTON_PRESS &&
!(bevent->state & GDK_SHIFT_MASK ) &&
!(bevent->state & GDK_CONTROL_MASK ) &&
dupe_listview_item_is_selected(dw, di, widget))
GtkTreeIter iter;
DupeItem *di = NULL;
- if (bevent->button != 1 && bevent->button != 2) return TRUE;
+ if (bevent->button != MOUSE_BUTTON_LEFT && bevent->button != MOUSE_BUTTON_MIDDLE) return TRUE;
store = gtk_tree_view_get_model(GTK_TREE_VIEW(widget));
gtk_tree_path_free(tpath);
}
- if (bevent->button == 2)
+ if (bevent->button == MOUSE_BUTTON_MIDDLE)
{
if (di && dw->click_item == di)
{
/* this overrides the low default of a GtkCellRenderer from 100 to CELL_HEIGHT_OVERRIDE, something sane for our purposes */
#define CELL_HEIGHT_OVERRIDE 512
-
+
void cell_renderer_height_override(GtkCellRenderer *renderer)
{
GParamSpec *spec;
column = gtk_tree_view_get_column(GTK_TREE_VIEW(listview), DUPE_COLUMN_THUMB - 1);
if (!column) return;
- gtk_tree_view_column_set_fixed_width(column, (thumb) ? thumb_max_width : 4);
-
+ gtk_tree_view_column_set_fixed_width(column, (thumb) ? options->thumbnails.max_width : 4);
+
list = gtk_tree_view_column_get_cell_renderers(column);
if (!list) return;
cell = list->data;
g_list_free(list);
- g_object_set(G_OBJECT(cell), "height", (thumb) ? thumb_max_height : -1, NULL);
+ g_object_set(G_OBJECT(cell), "height", (thumb) ? options->thumbnails.max_height : -1, NULL);
gtk_tree_view_columns_autosize(GTK_TREE_VIEW(listview));
}
file_util_delete(NULL, dupe_listview_get_selection(dw, listview), dw->window);
break;
case 'P': case 'p':
- info_window_new(NULL, dupe_listview_get_selection(dw, listview));
+ info_window_new(NULL, dupe_listview_get_selection(dw, listview), NULL);
break;
default:
stop_signal = FALSE;
break;
}
}
-
+#if 0
if (edit_val >= 0)
{
dupe_window_edit_selected(dw, edit_val);
}
+#endif
}
else
{
dupe_list_free(dw->second_list);
+ file_data_unregister_notify_func(dupe_notify_cb, dw);
+
g_free(dw);
}
dw->second_set = FALSE;
- dw->window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
- window_set_icon(dw->window, NULL, NULL);
+ dw->window = window_new(GTK_WINDOW_TOPLEVEL, "dupe", NULL, NULL, _("Find duplicates"));
- geometry.min_width = 32;
- geometry.min_height = 32;
+ geometry.min_width = DEFAULT_MINIMAL_WINDOW_SIZE;
+ geometry.min_height = DEFAULT_MINIMAL_WINDOW_SIZE;
geometry.base_width = DUPE_DEF_WIDTH;
geometry.base_height = DUPE_DEF_HEIGHT;
gtk_window_set_geometry_hints(GTK_WINDOW(dw->window), NULL, &geometry,
gtk_window_set_default_size(GTK_WINDOW(dw->window), DUPE_DEF_WIDTH, DUPE_DEF_HEIGHT);
gtk_window_set_resizable(GTK_WINDOW(dw->window), TRUE);
- gtk_window_set_title(GTK_WINDOW(dw->window), _("Find duplicates - Geeqie"));
- gtk_window_set_wmclass(GTK_WINDOW(dw->window), "dupe", GQ_WMCLASS);
- gtk_container_set_border_width (GTK_CONTAINER (dw->window), 0);
+ gtk_container_set_border_width(GTK_CONTAINER(dw->window), 0);
- g_signal_connect(G_OBJECT(dw->window), "delete_event",
+ g_signal_connect(G_OBJECT(dw->window), "delete_event",
G_CALLBACK(dupe_window_delete), dw);
g_signal_connect(G_OBJECT(dw->window), "key_press_event",
G_CALLBACK(dupe_window_keypress_cb), dw);
gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(scrolled), GTK_SHADOW_IN);
gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrolled), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
gtk_table_attach_defaults(GTK_TABLE(dw->table), scrolled, 0, 2, 0, 1);
- gtk_widget_show(scrolled);
+ gtk_widget_show(scrolled);
store = gtk_list_store_new(9, G_TYPE_POINTER, G_TYPE_STRING, GDK_TYPE_PIXBUF,
G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING,
gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(scrolled), GTK_SHADOW_IN);
gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrolled), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
gtk_box_pack_start(GTK_BOX(dw->second_vbox), scrolled, TRUE, TRUE, 0);
- gtk_widget_show(scrolled);
+ gtk_widget_show(scrolled);
store = gtk_list_store_new(2, G_TYPE_POINTER, G_TYPE_STRING);
dw->second_listview = gtk_tree_view_new_with_model(GTK_TREE_MODEL(store));
dupe_listview_add_column(dw, dw->second_listview, 1, _("Compare to:"), FALSE, FALSE);
gtk_container_add(GTK_CONTAINER(scrolled), dw->second_listview);
- gtk_widget_show(dw->second_listview);
+ gtk_widget_show(dw->second_listview);
dw->second_status_label = gtk_label_new("");
gtk_box_pack_start(GTK_BOX(dw->second_vbox), dw->second_status_label, FALSE, FALSE, 0);
gtk_widget_show(button);
status_box = gtk_hbox_new(FALSE, 0);
- gtk_box_pack_start(GTK_BOX(vbox), status_box, FALSE, FALSE, 0);
- gtk_widget_show(status_box);
+ gtk_box_pack_start(GTK_BOX(vbox), status_box, FALSE, FALSE, 0);
+ gtk_widget_show(status_box);
frame = gtk_frame_new(NULL);
gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_IN);
dupe_window_list = g_list_append(dupe_window_list, dw);
+ file_data_register_notify_func(dupe_notify_cb, dw, NOTIFY_PRIORITY_MEDIUM);
+
return dw;
}
work = work->next;
if (isdir(fd->path))
{
- GList *list = NULL;
+ GList *list;
- filelist_read(fd->path, &list, NULL);
+ filelist_read(fd, &list, NULL);
list = filelist_filter(list, FALSE);
if (list)
{
*/
static GtkTargetEntry dupe_drag_types[] = {
- { "text/uri-list", 0, TARGET_URI_LIST },
- { "text/plain", 0, TARGET_TEXT_PLAIN }
+ { "text/uri-list", 0, TARGET_URI_LIST },
+ { "text/plain", 0, TARGET_TEXT_PLAIN }
};
static gint n_dupe_drag_types = 2;
static GtkTargetEntry dupe_drop_types[] = {
- { "application/x-gqview-collection-member", 0, TARGET_APP_COLLECTION_MEMBER },
- { "text/uri-list", 0, TARGET_URI_LIST }
+ { TARGET_APP_COLLECTION_MEMBER_STRING, 0, TARGET_APP_COLLECTION_MEMBER },
+ { "text/uri-list", 0, TARGET_URI_LIST }
};
static gint n_dupe_drop_types = 2;
case TARGET_URI_LIST:
list = uri_filelist_from_text((gchar *)selection_data->data, TRUE);
work = list;
- while(work)
+ while (work)
{
FileData *fd = work->data;
if (isdir(fd->path))
*-------------------------------------------------------------------
*/
-void dupe_maint_removed(FileData *fd)
+static void dupe_notify_cb(FileData *fd, NotifyType type, gpointer data)
{
- GList *work;
-
- work = dupe_window_list;
- while (work)
- {
- DupeWindow *dw = work->data;
- work = work->next;
-
- while (dupe_item_remove_by_path(dw, fd->path));
- }
-}
-
-void dupe_maint_renamed(FileData *fd)
-{
- GList *work;
+ DupeWindow *dw = data;
- work = dupe_window_list;
- while (work)
+ if (type != NOTIFY_TYPE_CHANGE || !fd->change) return;
+
+ switch(fd->change->type)
{
- DupeWindow *dw = work->data;
- work = work->next;
-
- dupe_item_update_fd(dw, fd);
+ case FILEDATA_CHANGE_MOVE:
+ case FILEDATA_CHANGE_RENAME:
+ dupe_item_update_fd(dw, fd);
+ break;
+ case FILEDATA_CHANGE_COPY:
+ break;
+ case FILEDATA_CHANGE_DELETE:
+ while (dupe_item_remove_by_path(dw, fd->path));
+ break;
+ case FILEDATA_CHANGE_UNSPECIFIED:
+ case FILEDATA_CHANGE_WRITE_METADATA:
+ break;
}
}
-
+/* vim: set shiftwidth=8 softtabstop=0 cindent cinoptions={1s: */