4e6d5c32ef9370ebdc66ccdcda88241069a4928b
[captive.git] / src / client / bug-replay / main.c
1 /* $Id$
2  * developer replaying of bugreport snapshots
3  * Copyright (C) 2003 Jan Kratochvil <project-captive@jankratochvil.net>
4  * 
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; exactly version 2 of June 1991 is required
8  * 
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  * 
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17  */
18
19
20 #include "config.h"
21
22 #include <glib/gmessages.h>
23 #include <stdlib.h>
24 #include <glib/giochannel.h>
25 #include <popt.h>
26 #include <string.h>
27 #include <stdio.h>
28 #include <libxml/xmlreader.h>
29 #include <glib-object.h>        /* for g_type_init() */
30 #include <glib/ghash.h>
31
32 #include <captive/client.h>
33 #include <captive/libxml.h>
34 #include <captive/options.h>
35 #include <captive/macros.h>
36 #include "../../libcaptive/client/giochannel-blind.h"   /* FIXME: pathname */
37 #include <captive/client-vfs.h>
38 #include <captive/client-directory.h>
39 #include <captive/client-file.h>
40
41
42 static gchar *optarg_module_path;
43
44 static const struct poptOption popt_table[]={
45 #define BUG_REPLAY_POPT(longname,argInfoP,argP,descripP,argDescripP) \
46                 { \
47                         longName: (longname), \
48                         shortName: 0, \
49                         argInfo: (argInfoP), \
50                         arg: (void *)argP, \
51                         val: 0, \
52                         descrip: (descripP), \
53                         argDescrip: (argDescripP), \
54                 }
55
56                 BUG_REPLAY_POPT("module-path",POPT_ARG_STRING,&optarg_module_path,N_("Disk path for W32 modules and filesystem"),N_("path")),
57
58 #undef BUG_REPLAY_POPT
59                 POPT_AUTOHELP
60                 POPT_TABLEEND
61                 };
62
63
64 static void object_hash_key_destroy_func(const xmlChar *xml_object)
65 {
66         g_return_if_fail(xml_object!=NULL);
67
68         xmlFree((xmlChar *)xml_object);
69 }
70
71 static void object_hash_value_destroy_func(GObject *captive_any_object)
72 {
73         g_return_if_fail(G_IS_OBJECT(captive_any_object));
74
75         g_object_unref(captive_any_object);
76 }
77
78
79 int main(int argc,char **argv)
80 {
81 poptContext context;
82 int errint;
83 const char **cmd_argv;
84 struct captive_options options;
85 xmlTextReader *xml_reader;
86 GList *action_list;     /* of 'xmlNode *' */
87 gboolean preread;
88 gboolean module_is_filesystem=FALSE;
89 CaptiveVfsObject *captive_vfs_object;
90 gboolean action_is_first;
91 xmlNode *xml_node;
92 GHashTable *object_hash;
93 GObject *object;
94 gboolean errbool;
95 CaptiveDirectoryObject *captive_directory_object;
96 CaptiveFileObject *captive_file_object;
97 GnomeVFSResult errgnomevfsresult;
98 struct captive_libxml_string_drop_stack *drop_stack=NULL;
99 const gchar *xml_object;
100
101         captive_standalone_init();
102
103         captive_options_init(&options);
104
105         context=poptGetContext(
106                         PACKAGE,        /* name */
107                         argc,(/*en-const*/const char **)argv,   /* argc,argv */
108                         popt_table,     /* options */
109                         POPT_CONTEXT_POSIXMEHARDER);    /* flags; && !POPT_CONTEXT_KEEP_FIRST */
110         if (context==NULL) {
111                 g_assert_not_reached(); /* argument recognization args_error */
112                 return EXIT_FAILURE;
113                 }
114         errint=poptReadDefaultConfig(context,
115                         TRUE);  /* useEnv */
116         if (errint!=0) {
117                 g_assert_not_reached(); /* argument recognization args_error */
118                 return EXIT_FAILURE;
119                 }
120         errint=poptGetNextOpt(context);
121         if (errint!=-1) {
122                 g_assert_not_reached(); /* some non-callbacked argument reached */
123                 return EXIT_FAILURE;
124                 }
125         cmd_argv=poptGetArgs(context);
126
127         if (!cmd_argv || !cmd_argv[0] || cmd_argv[1]) {
128                 g_error("Exactly one argument required - pathname to .captivebug.xml.gz bugreport to replay");
129                 return EXIT_FAILURE;
130                 }
131
132   options.rwmode=CAPTIVE_OPTION_RWMODE_BLIND;
133   options.debug_messages=TRUE;
134
135         options.image_iochannel=NULL;
136         action_list=NULL;
137         options.media=CAPTIVE_OPTION_MEDIA_UNKNOWN;
138
139         xml_reader=xmlNewTextReaderFilename(cmd_argv[0]);
140         g_assert(xml_reader!=NULL);
141         preread=FALSE;
142         while (preread || 1==xmlTextReaderRead(xml_reader)) {
143                 preread=FALSE;
144                 switch (xmlTextReaderNodeType(xml_reader)) {
145
146                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_COMMENT:
147                                 break;
148
149                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_SIGNIFICANT_WHITESPACE:
150                                 break;
151
152                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_TEXT:    /* Even empty nodes have some '#text'. */
153                                 break;
154
155                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_END:     /* We do not track tag ends. */
156                                 break;
157
158                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_START: {
159 const xmlChar *xml_name;
160
161                                 xml_name=xmlTextReaderName(xml_reader);
162                                 /**/ if (!xmlStrcmp(xml_name,BAD_CAST "bug")) { /* root tag */
163                                         }
164                                 else if (!xmlStrcmp(xml_name,BAD_CAST "captive")) {
165 const gchar *xml_captive_version;
166
167                                         xml_captive_version=captive_libxml_string_drop(&drop_stack,xmlTextReaderGetAttribute(xml_reader,BAD_CAST "version"));
168                                         g_assert(xml_captive_version!=NULL);
169                                         g_assert(!strcmp(xml_captive_version,VERSION));
170                                         }
171                                 else if (!xmlStrcmp(xml_name,BAD_CAST "filesystem")) {  /* contains <module/> */
172                                         module_is_filesystem=TRUE;
173                                         }
174                                 else if (!xmlStrcmp(xml_name,BAD_CAST "load_module")) { /* contains <module/> */
175                                         module_is_filesystem=FALSE;
176                                         }
177                                 else if (!xmlStrcmp(xml_name,BAD_CAST "module")) {
178 const gchar *xml_module_basename;
179 struct captive_options_module *options_module;
180 gboolean errbool;
181
182                                         if (module_is_filesystem)
183                                                 options_module=&options.filesystem;
184                                         else {
185                                                 captive_new(options_module);
186                                                 options.load_module=g_list_append(options.load_module,options_module);
187                                                 }
188                                         xml_module_basename=captive_libxml_string_drop(&drop_stack,xmlTextReaderGetAttribute(xml_reader,BAD_CAST "basename"));
189                                         g_assert(xml_module_basename!=NULL);
190                                         g_assert(strchr(xml_module_basename,'/')==NULL);        /* a bit of security */
191                                         errbool=captive_options_module_load(options_module,
192                                                         captive_printf_alloca("%s/%s",
193                                                                         (optarg_module_path ? optarg_module_path : "."),xml_module_basename));
194                                         g_assert(errbool==TRUE);
195                                         switch (options_module->type) {
196                                                 case CAPTIVE_OPTIONS_MODULE_TYPE_PE32: {
197 const gchar *xml_module_md5,*xml_module_length;
198
199                                                         if (options_module->u.pe32.md5
200                                                                         && (xml_module_md5=captive_libxml_string_drop(&drop_stack,xmlTextReaderGetAttribute(xml_reader,BAD_CAST "version"))))
201                                                                 g_assert(!strcmp(xml_module_md5,options_module->u.pe32.md5));
202                                                         if ((xml_module_length=captive_libxml_string_drop(&drop_stack,xmlTextReaderGetAttribute(xml_reader,BAD_CAST "length"))))
203                                                                 g_assert(!strcmp(xml_module_length,
204                                                                                 captive_printf_alloca("%lu",(unsigned long)options_module->u.pe32.length)));
205                                                         } break;
206                                                 case CAPTIVE_OPTIONS_MODULE_TYPE_GMODULE:
207                                                         /* No possibility to check anything. */
208                                                         break;
209                                                 default: g_assert_not_reached();
210                                                 }
211                                         }
212                                 else if (!xmlStrcmp(xml_name,BAD_CAST "action")) {
213 int xml_action_depth;
214 gboolean action_done,action_preread;
215
216                                         g_assert(action_list==NULL);
217                                         xml_action_depth=xmlTextReaderDepth(xml_reader);
218                                         action_preread=FALSE;
219                                         action_done=FALSE;
220                                         while (!action_done) {
221                                                 if (!action_preread) {
222                                                         errint=xmlTextReaderRead(xml_reader);
223                                                         g_assert(errint==1);
224                                                         }
225                                                 action_preread=FALSE;
226                                                 g_assert(xml_action_depth<=xmlTextReaderDepth(xml_reader));
227                                                 switch (xmlTextReaderNodeType(xml_reader)) {
228                                                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_COMMENT:
229                                                                 break;
230                                                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_SIGNIFICANT_WHITESPACE:
231                                                                 break;
232                                                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_TEXT:    /* Even empty nodes have some '#text'. */
233                                                                 break;
234                                                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_END: {   /* We do not track tag ends. */
235                                                                 if ((action_done=(xml_action_depth==xmlTextReaderDepth(xml_reader)))) {
236 const gchar *xml_name_end;
237
238                                                                         xml_name_end=captive_libxml_string_drop(&drop_stack,xmlTextReaderName(xml_reader));
239                                                                         g_assert(!strcmp(xml_name_end,"action"));
240                                                                         }
241                                                                 } break;
242                                                         case CAPTIVE_XML_TEXT_READER_NODE_TYPE_START: {
243 xmlNode *xml_node;
244                                                                 
245                                                                 xml_node=xmlTextReaderExpand(xml_reader);
246                                                                 g_assert(xml_node!=NULL);
247                                                                 xml_node=xmlCopyNode(xml_node,
248                                                                                 1);     /* recursive */
249                                                                 errint=xmlTextReaderNext(xml_reader);
250                                                                 g_assert(errint==1);
251                                                                 action_preread=TRUE;
252                                                                 action_list=g_list_prepend(action_list,xml_node);       /* we are prepending to be effective */
253                                                                 } break;
254                                                         default: g_assert_not_reached();
255                                                         }
256                                                 }
257                                         }
258                                 else if (!xmlStrcmp(xml_name,BAD_CAST "media")) {
259 const xmlChar *xml_media_end_name,*xml_media_type;
260
261                                         g_assert(options.image_iochannel==NULL);
262                                         options.image_iochannel=(GIOChannel *)captive_giochannel_blind_new_from_xml(xml_reader);
263                                         g_assert(CAPTIVE_XML_TEXT_READER_NODE_TYPE_END==xmlTextReaderNodeType(xml_reader));
264                                         xml_media_end_name=xmlTextReaderName(xml_reader);
265                                         g_assert(xml_media_end_name!=NULL);
266                                         g_assert(!xmlStrcmp(xml_media_end_name,BAD_CAST "media"));
267                                         xmlFree((xmlChar *)xml_media_end_name);
268                                         xml_media_type=xmlTextReaderGetAttribute(xml_reader,BAD_CAST "type");
269                                         g_assert(xml_media_type!=NULL);
270                                         /**/ if (!xmlStrcmp(xml_media_type,BAD_CAST "cdrom"))
271                                                 options.media=CAPTIVE_OPTION_MEDIA_CDROM;
272                                         else if (!xmlStrcmp(xml_media_type,BAD_CAST "disk"))
273                                                 options.media=CAPTIVE_OPTION_MEDIA_DISK;
274                                         else g_assert_not_reached();
275                                         xmlFree((xmlChar *)xml_media_type);
276                                         }
277                                 else if (!xmlStrcmp(xml_name,BAD_CAST "log")) {
278                                         errint=xmlTextReaderNext(xml_reader);
279                                         g_assert(errint==1);
280                                         preread=TRUE;
281                                         }
282                                 else g_error("Unknown START node: %s",xml_name);
283                                 xmlFree((xmlChar *)xml_name);
284                                 } break;
285
286                         default: g_assert_not_reached();
287                         }
288                 captive_libxml_string_drop_flush(&drop_stack);
289                 }
290         xmlFreeTextReader(xml_reader);
291
292         g_assert(options.image_iochannel!=NULL);
293         action_list=g_list_reverse(action_list);        /* we were g_list_prepend()ing for effectivity */
294         g_assert(options.media!=CAPTIVE_OPTION_MEDIA_UNKNOWN);
295
296         if (GNOME_VFS_OK!=captive_vfs_new(&captive_vfs_object,&options)) {
297                 g_error(_("captive_vfs_new() failed"));
298                 return EXIT_FAILURE;
299                 }
300         captive_options_free(&options);
301
302         /* 'cmd_argv' gets cleared by 'poptFreeContext(context);' below */
303         poptFreeContext(context);
304
305   object_hash=g_hash_table_new_full(
306                         g_str_hash,     /* hash_func */
307                         g_str_equal,    /* key_equal_func */
308                         (GDestroyNotify)object_hash_key_destroy_func,   /* key_destroy_func */
309                         (GDestroyNotify)object_hash_value_destroy_func);        /* value_destroy_func */
310
311         for (
312                         action_is_first=TRUE;
313                         action_list;
314                         xmlFreeNode(xml_node),action_is_first=FALSE) {
315
316                 captive_libxml_string_drop_flush(&drop_stack);
317
318 #define GET_PROP_STRING(prop_name) ({ \
319                 const gchar *_get_prop_string_r=captive_libxml_string_drop(&drop_stack,xmlGetProp(xml_node,BAD_CAST (prop_name))); \
320                 g_assert(_get_prop_string_r!=NULL); \
321                 _get_prop_string_r; \
322                 })
323 #define GET_PROP_GINT64(prop_name) (captive_libxml_sscanf_gint64(GET_PROP_STRING((prop_name))))
324
325                 xml_node=action_list->data;
326                 g_assert(xml_node!=NULL);
327                 action_list=g_list_delete_link(action_list,action_list);
328                 g_message("replay action: %s()",xml_node->name);
329                 xml_object=GET_PROP_STRING("object");
330                 object=g_hash_table_lookup(object_hash,xml_object);
331                 g_assert(object==NULL || G_IS_OBJECT(object));
332
333                 if (!xmlStrcmp(xml_node->name,BAD_CAST "vfs_new")) {
334                         g_assert(action_is_first==TRUE);
335                         g_assert(captive_vfs_object!=NULL);
336                         g_assert(object==NULL);
337                         g_hash_table_insert(object_hash,g_strdup(xml_object),captive_vfs_object);
338                         continue;
339                         }
340                 if (!xmlStrcmp(xml_node->name,BAD_CAST "vfs_commit")) {
341                         g_assert(action_is_first==TRUE);
342                         g_assert(captive_vfs_object!=NULL);
343                         g_assert(object==NULL);
344                         g_hash_table_insert(object_hash,g_strdup(xml_object),captive_vfs_object);
345                         continue;
346                         }
347                 g_assert(action_is_first==FALSE);
348                 if (!xmlStrcmp(xml_node->name,BAD_CAST "vfs_close")) {
349                         g_assert(captive_vfs_object!=NULL);
350                         g_assert(CAPTIVE_VFS_OBJECT(object)==captive_vfs_object);
351                         errbool=g_hash_table_remove(object_hash,xml_object);    /* g_object_unref() by object_hash_value_destroy_func() */
352                         g_assert(errbool==TRUE);
353                         continue;
354                         }
355                 g_assert(captive_vfs_object!=NULL);
356                 if (!xmlStrcmp(xml_node->name,BAD_CAST "vfs_volume_info_get")) {
357 CaptiveVfsVolumeInfo volume_info;
358
359                         errgnomevfsresult=captive_vfs_volume_info_get(captive_vfs_object,&volume_info);
360                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
361                         continue;
362                         }
363
364                 /* DIRECTORY */
365                 if (!xmlStrcmp(xml_node->name,BAD_CAST "directory_new_open")) {
366                         g_assert(object==NULL);
367                         errgnomevfsresult=captive_directory_new_open(&captive_directory_object,captive_vfs_object,
368                                         GET_PROP_STRING("pathname"));
369                         g_assert((errgnomevfsresult==GNOME_VFS_OK)==GET_PROP_GINT64("result"));
370                         if (errgnomevfsresult==GNOME_VFS_OK)
371                                 g_hash_table_insert(object_hash,g_strdup(xml_object),captive_directory_object);
372                         continue;
373                         }
374                 if (!xmlStrcmp(xml_node->name,BAD_CAST "directory_new_make")) {
375                         g_assert(object==NULL);
376                         errgnomevfsresult=captive_directory_new_make(&captive_directory_object,captive_vfs_object,
377                                         GET_PROP_STRING("pathname"),
378                                         GET_PROP_GINT64("perm"));
379                         g_assert((errgnomevfsresult==GNOME_VFS_OK)==GET_PROP_GINT64("result"));
380                         if (errgnomevfsresult==GNOME_VFS_OK)
381                                 g_hash_table_insert(object_hash,g_strdup(xml_object),captive_directory_object);
382                         continue;
383                         }
384                 if (!xmlStrcmp(xml_node->name,BAD_CAST "directory_close")) {
385                         captive_directory_object=CAPTIVE_DIRECTORY_OBJECT(object);
386                         errbool=g_hash_table_remove(object_hash,xml_object);    /* g_object_unref() by object_hash_value_destroy_func() */
387                         g_assert(errbool==TRUE);
388                         continue;
389                         }
390                 if (!xmlStrcmp(xml_node->name,BAD_CAST "directory_read")) {
391 CaptiveFileInfoObject *captive_file_info_object;
392
393                         captive_directory_object=CAPTIVE_DIRECTORY_OBJECT(object);
394                         errgnomevfsresult=captive_directory_read(captive_directory_object,&captive_file_info_object);
395                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
396                         if (GNOME_VFS_OK==errgnomevfsresult)
397                                 g_object_unref(captive_file_info_object);
398                         continue;
399                         }
400                 if (!xmlStrcmp(xml_node->name,BAD_CAST "directory_remove")) {
401                         captive_directory_object=CAPTIVE_DIRECTORY_OBJECT(object);
402                         errgnomevfsresult=captive_directory_remove(captive_directory_object);
403                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
404                         continue;
405                         }
406
407                 /* FILE */
408                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_new_open")) {
409                         g_assert(object==NULL);
410                         errgnomevfsresult=captive_file_new_open(&captive_file_object,captive_vfs_object,
411                                         GET_PROP_STRING("pathname"),
412                                         GET_PROP_GINT64("mode"));
413                         g_assert((errgnomevfsresult==GNOME_VFS_OK)==GET_PROP_GINT64("result"));
414                         if (errgnomevfsresult==GNOME_VFS_OK)
415                                 g_hash_table_insert(object_hash,g_strdup(xml_object),captive_file_object);
416                         continue;
417                         }
418                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_new_create")) {
419                         g_assert(object==NULL);
420                         errgnomevfsresult=captive_file_new_create(&captive_file_object,captive_vfs_object,
421                                         GET_PROP_STRING("pathname"),
422                                         GET_PROP_GINT64("mode"),
423                                         GET_PROP_GINT64("exclusive"),
424                                         GET_PROP_GINT64("perm"));
425                         g_assert((errgnomevfsresult==GNOME_VFS_OK)==GET_PROP_GINT64("result"));
426                         if (errgnomevfsresult==GNOME_VFS_OK)
427                                 g_hash_table_insert(object_hash,g_strdup(xml_object),captive_file_object);
428                         continue;
429                         }
430                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_close")) {
431                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
432                         errbool=g_hash_table_remove(object_hash,xml_object);    /* g_object_unref() by object_hash_value_destroy_func() */
433                         g_assert(errbool==TRUE);
434                         continue;
435                         }
436                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_read")) {
437 gpointer buffer;
438 GnomeVFSFileSize num_bytes,bytes_read;
439
440                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
441                         num_bytes=GET_PROP_GINT64("num_bytes");
442                         buffer=g_malloc(num_bytes);
443                         errgnomevfsresult=captive_file_read(captive_file_object,buffer,num_bytes,&bytes_read);
444                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
445                         if (errgnomevfsresult==GNOME_VFS_OK)
446                                 g_assert((gint64)bytes_read==GET_PROP_GINT64("bytes_read_return"));
447                         g_free(buffer);
448                         continue;
449                         }
450                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_write")) {
451 gpointer buffer;
452 GnomeVFSFileSize num_bytes,bytes_written;
453
454                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
455                         num_bytes=GET_PROP_GINT64("num_bytes");
456                         buffer=g_malloc(num_bytes);
457                         memset(buffer,'X',num_bytes);   /* FIXME: better pattern */
458                         errgnomevfsresult=captive_file_write(captive_file_object,buffer,num_bytes,&bytes_written);
459                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
460                         if (errgnomevfsresult==GNOME_VFS_OK)
461                                 g_assert((gint64)bytes_written==GET_PROP_GINT64("bytes_written_return"));
462                         g_free(buffer);
463                         continue;
464                         }
465                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_seek")) {
466 GnomeVFSSeekPosition whence=GNOME_VFS_SEEK_START;       /* Prevent: ... might be used uninitialized in this function */
467 const gchar *whence_string;
468
469                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
470                         whence_string=GET_PROP_STRING("whence");
471                         /**/ if (!strcmp(whence_string,"start"  )) whence=GNOME_VFS_SEEK_START;
472                         else if (!strcmp(whence_string,"current")) whence=GNOME_VFS_SEEK_CURRENT;
473                         else if (!strcmp(whence_string,"end"    )) whence=GNOME_VFS_SEEK_END;
474                         else g_assert_not_reached();
475                         errgnomevfsresult=captive_file_seek(captive_file_object,whence,
476                                         GET_PROP_GINT64("offset"));
477                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
478                         continue;
479                         }
480                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_tell")) {
481 GnomeVFSFileOffset offset;
482
483                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
484                         errgnomevfsresult=captive_file_tell(captive_file_object,&offset);
485                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
486                         if (errgnomevfsresult==GNOME_VFS_OK)
487                                 g_assert((gint64)offset==GET_PROP_GINT64("offset"));
488                         continue;
489                         }
490                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_remove")) {
491                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
492                         errgnomevfsresult=captive_file_remove(captive_file_object);
493                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
494                         continue;
495                         }
496                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_file_info_get")) {
497 CaptiveFileInfoObject *captive_file_info_object;
498
499                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
500                         errgnomevfsresult=captive_file_file_info_get(captive_file_object,&captive_file_info_object);
501                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
502                         if (GNOME_VFS_OK==errgnomevfsresult)
503                                 g_object_unref(captive_file_info_object);
504                         continue;
505                         }
506                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_file_info_set")) {
507 CaptiveFileInfoObject *captive_file_info_object;
508
509                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
510                         /* FIXME: We do not have 'captive_file_info_object' content in the bug file! */
511                         errgnomevfsresult=captive_file_file_info_get(captive_file_object,&captive_file_info_object);
512                         g_assert(errgnomevfsresult==GNOME_VFS_OK);
513                         errgnomevfsresult=captive_file_file_info_set(captive_file_object,captive_file_info_object,
514                                         GET_PROP_GINT64("mask"));
515                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
516                         g_object_unref(captive_file_info_object);
517                         continue;
518                         }
519                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_truncate")) {
520                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
521                         errgnomevfsresult=captive_file_truncate(captive_file_object,
522                                         GET_PROP_GINT64("file_size"));
523                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
524                         continue;
525                         }
526                 if (!xmlStrcmp(xml_node->name,BAD_CAST "file_move")) {
527                         captive_file_object=CAPTIVE_FILE_OBJECT(object);
528                         errgnomevfsresult=captive_file_move(captive_file_object,
529                                         GET_PROP_STRING("pathname_new"),
530                                         GET_PROP_GINT64("force_replace"));
531                         g_assert(!strcmp(gnome_vfs_result_to_string(errgnomevfsresult),GET_PROP_STRING("result")));
532                         continue;
533                         }
534
535                 g_error("Unknown action: %s()",xml_node->name);
536
537 #undef GET_PROP_GINT64
538 #undef GET_PROP_STRING
539                 }
540
541         g_error("All actions were processed, no vfs_close() found");
542         return EXIT_FAILURE;
543 }