source: trunk/third/GConf/gconf/gconftool.c @ 17087

Revision 17087, 61.0 KB checked in by ghudson, 22 years ago (diff)
This commit was generated by cvs2svn to compensate for changes in r17086, which included commits to RCS files with non-trunk default branches.
Line 
1/* GConf
2 * Copyright (C) 1999, 2000 Red Hat Inc.
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
8 *
9 * This library 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 GNU
12 * Library General Public License for more details.
13 *
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
18 */
19
20#include "gconf.h"
21#include "gconf-internals.h"
22#include <stdio.h>
23#include <unistd.h>
24#include <popt.h>
25#include <libxml/tree.h>
26#include <libxml/parser.h>
27#include <libxml/xmlmemory.h>
28#include <stdlib.h>
29#include <errno.h>
30
31static int set_mode = FALSE;
32static int get_mode = FALSE;
33static int unset_mode = FALSE;
34static int all_entries_mode = FALSE;
35static int all_subdirs_mode = FALSE;
36static char* dir_exists = NULL;
37static int recursive_list = FALSE;
38static int set_schema_mode = FALSE;
39static char* value_type = NULL;
40static char* value_list_type = NULL;
41static char* value_car_type = NULL;
42static char* value_cdr_type = NULL;
43static int shutdown_gconfd = FALSE;
44static int ping_gconfd = FALSE;
45static int spawn_gconfd = FALSE;
46static char* short_desc = NULL;
47static char* long_desc = NULL;
48static char* owner = NULL;
49static char* schema_file = NULL;
50static char* config_source = NULL;
51static int use_local_source = FALSE;
52static int makefile_install_mode = FALSE;
53static int break_key_mode = FALSE;
54static int break_dir_mode = FALSE;
55static int short_docs_mode = FALSE;
56static int long_docs_mode = FALSE;
57static int schema_name_mode = FALSE;
58static int associate_schema_mode = FALSE;
59static int default_source_mode = FALSE;
60
61struct poptOption options[] = {
62  {
63    NULL,
64    '\0',
65    POPT_ARG_INCLUDE_TABLE,
66    poptHelpOptions,
67    0,
68    N_("Help options"),
69    NULL
70  },
71  {
72    "set",
73    's',
74    POPT_ARG_NONE,
75    &set_mode,
76    0,
77    N_("Set a key to a value and sync. Use with --type."),
78    NULL
79  },
80  {
81    "get",
82    'g',
83    POPT_ARG_NONE,
84    &get_mode,
85    0,
86    N_("Print the value of a key to standard output."),
87    NULL
88  },
89  {
90    "set-schema",
91    '\0',
92    POPT_ARG_NONE,
93    &set_schema_mode,
94    0,
95    N_("Set a schema and sync. Use with --short-desc, --long-desc, --owner, and --type."),
96    NULL
97  },
98  {
99
100    "unset",
101    'u',
102    POPT_ARG_NONE,
103    &unset_mode,
104    0,
105    N_("Unset the keys on the command line"),
106    NULL
107  },
108  {
109    "all-entries",
110    'a',
111    POPT_ARG_NONE,
112    &all_entries_mode,
113    0,
114    N_("Print all key/value pairs in a directory."),
115    NULL
116  },
117  {
118    "all-dirs",
119    '\0',
120    POPT_ARG_NONE,
121    &all_subdirs_mode,
122    0,
123    N_("Print all subdirectories in a directory."),
124    NULL
125  },
126  {
127    "recursive-list",
128    'R',
129    POPT_ARG_NONE,
130    &recursive_list,
131    0,
132    N_("Print all subdirectories and entries under a dir, recursively."),
133    NULL
134  },
135  {
136    "dir-exists",
137    '\0',
138    POPT_ARG_STRING,
139    &dir_exists,
140    0,
141    N_("Return 0 if the directory exists, 2 if it does not."),
142    NULL
143  },
144  {
145    "shutdown",
146    '\0',
147    POPT_ARG_NONE,
148    &shutdown_gconfd,
149    0,
150    N_("Shut down gconfd. DON'T USE THIS OPTION WITHOUT GOOD REASON."),
151    NULL
152  },
153  {
154    "ping",
155    'p',
156    POPT_ARG_NONE,
157    &ping_gconfd,
158    0,
159    N_("Return 0 if gconfd is running, 2 if not."),
160    NULL
161  },
162  {
163    "spawn",
164    '\0',
165    POPT_ARG_NONE,
166    &spawn_gconfd,
167    0,
168    N_("Launch the config server (gconfd). (Normally happens automatically when needed.)"),
169    NULL
170  },
171  {
172    "type",
173    't',
174    POPT_ARG_STRING,
175    &value_type,
176    0,
177    N_("Specify the type of the value being set, or the type of the value a schema describes. Unique abbreviations OK."),
178    N_("int|bool|float|string|list|pair")
179  }, 
180  {
181    "list-type",
182    '\0',
183    POPT_ARG_STRING,
184    &value_list_type,
185    0,
186    N_("Specify the type of the list value being set, or the type of the value a schema describes. Unique abbreviations OK."),
187    N_("int|bool|float|string")
188  }, 
189  {
190    "car-type",
191    '\0',
192    POPT_ARG_STRING,
193    &value_car_type,
194    0,
195    N_("Specify the type of the car pair value being set, or the type of the value a schema describes. Unique abbreviations OK."),
196    N_("int|bool|float|string")
197  }, 
198  {
199    "cdr-type",
200    '\0',
201    POPT_ARG_STRING,
202    &value_cdr_type,
203    0,
204    N_("Specify the type of the cdr pair value being set, or the type of the value a schema describes. Unique abbreviations OK."),
205    N_("int|bool|float|string")
206  }, 
207  {
208    "short-desc",
209    '\0',
210    POPT_ARG_STRING,
211    &short_desc,
212    0,
213    N_("Specify a short half-line description to go in a schema."),
214    N_("DESCRIPTION")
215  },
216  {
217    "long-desc",
218    '\0',
219    POPT_ARG_STRING,
220    &long_desc,
221    0,
222    N_("Specify a several-line description to go in a schema."),
223    N_("DESCRIPTION")
224  },
225  {
226    "owner",
227    '\0',
228    POPT_ARG_STRING,
229    &owner,
230    0,
231    N_("Specify the owner of a schema"),
232    N_("OWNER")
233  },
234  {
235    "install-schema-file",
236    '\0',
237    POPT_ARG_STRING,
238    &schema_file,
239    0,
240    N_("Specify a schema file to be installed"),
241    N_("FILENAME")
242  },
243  {
244    "config-source",
245    '\0',
246    POPT_ARG_STRING,
247    &config_source,
248    0,
249    N_("Specify a configuration source to use rather than the default path"),
250    N_("SOURCE")
251  },
252  {
253    "direct",
254    '\0',
255    POPT_ARG_NONE,
256    &use_local_source,
257    0,
258    N_("Access the config database directly, bypassing server. Requires that gconfd is not running."),
259    NULL
260  },
261  {
262    "makefile-install-rule",
263    '\0',
264    POPT_ARG_NONE,
265    &makefile_install_mode,
266    0,
267    N_("Properly installs schema files on the command line into the database. GCONF_CONFIG_SOURCE environment variable should be set to a non-default config source or set to the empty string to use the default."),
268    NULL
269  },
270  {
271    "break-key",
272    '\0',
273    POPT_ARG_NONE,
274    &break_key_mode,
275    0,
276    N_("Torture-test an application by setting and unsetting a bunch of values of different types for keys on the command line."),
277    NULL
278  },
279  {
280    "break-directory",
281    '\0',
282    POPT_ARG_NONE,
283    &break_dir_mode,
284    0,
285    N_("Torture-test an application by setting and unsetting a bunch of keys inside the directories on the command line."),
286    NULL
287  },
288  {
289    "short-docs",
290    '\0',
291    POPT_ARG_NONE,
292    &short_docs_mode,
293    0,
294    N_("Get the short doc string for a key"),
295    NULL
296  },
297  {
298    "long-docs",
299    '\0',
300    POPT_ARG_NONE,
301    &long_docs_mode,
302    0,
303    N_("Get the long doc string for a key"),
304    NULL
305  },
306  {
307    "get-schema-name",
308    '\0',
309    POPT_ARG_NONE,
310    &schema_name_mode,
311    0,
312    N_("Get the name of the schema applied to this key"),
313    NULL
314  },
315  {
316    "apply-schema",
317    '\0',
318    POPT_ARG_NONE,
319    &associate_schema_mode,
320    0,
321    N_("Specify the schema name followed by the key to apply the schema name to"),
322    NULL
323  },
324  {
325    "get-default-source",
326    '\0',
327    POPT_ARG_NONE,
328    &default_source_mode,
329    0,
330    N_("Get the name of the default source"),
331    NULL
332  },
333  {
334    NULL,
335    '\0',
336    0,
337    NULL,
338    0,
339    NULL,
340    NULL
341  }
342};
343
344static int do_break_key(GConfEngine* conf, const gchar** args);
345static int do_break_directory(GConfEngine* conf, const gchar** args);
346static int do_makefile_install(GConfEngine* conf, const gchar** args);
347static int do_recursive_list(GConfEngine* conf, const gchar** args);
348static int do_all_pairs(GConfEngine* conf, const gchar** args);
349static void list_pairs_in_dir(GConfEngine* conf, const gchar* dir, guint depth);
350static gboolean do_dir_exists(GConfEngine* conf, const gchar* dir);
351static void do_spawn_daemon(GConfEngine* conf);
352static int do_get(GConfEngine* conf, const gchar** args);
353static int do_set(GConfEngine* conf, const gchar** args);
354static int do_set_schema(GConfEngine* conf, const gchar** args);
355static int do_all_entries(GConfEngine* conf, const gchar** args);
356static int do_unset(GConfEngine* conf, const gchar** args);
357static int do_all_subdirs(GConfEngine* conf, const gchar** args);
358static int do_load_schema_file(GConfEngine* conf, const gchar* file);
359static int do_short_docs (GConfEngine *conf, const gchar **args);
360static int do_long_docs (GConfEngine *conf, const gchar **args);
361static int do_get_schema_name (GConfEngine *conf, const gchar **args);
362static int do_associate_schema (GConfEngine *conf, const gchar **args);
363static int do_get_default_source (GConfEngine *conf, const gchar **args);
364
365int
366main (int argc, char** argv)
367{
368  GConfEngine* conf;
369  poptContext ctx;
370  gint nextopt;
371  GError* err = NULL;
372 
373  ctx = poptGetContext("gconftool", argc, argv, options, 0);
374
375  poptReadDefaultConfig(ctx, TRUE);
376
377  while((nextopt = poptGetNextOpt(ctx)) > 0)
378    /*nothing*/;
379
380  if(nextopt != -1)
381    {
382      fprintf(stderr, _("Error on option %s: %s.\nRun '%s --help' to see a full list of available command line options.\n"),
383              poptBadOption(ctx, 0),
384              poptStrerror(nextopt),
385              argv[0]);
386      return 1;
387    }
388
389  /* Um, this is a mess. Not using popt right? */
390
391  if ((get_mode && set_mode) ||
392      (get_mode && unset_mode))
393    {
394      fprintf(stderr, _("Can't get and set/unset simultaneously\n"));
395      return 1;
396    }
397
398  if ((set_mode && get_mode) ||
399      (set_mode && unset_mode))
400    {
401      fprintf(stderr, _("Can't set and get/unset simultaneously\n"));
402      return 1;
403    }
404
405  if ((all_entries_mode && get_mode) ||
406      (all_entries_mode && set_mode) ||
407      (all_entries_mode && unset_mode))
408    {
409      fprintf(stderr, _("Can't use --all-entries with --get or --set\n"));
410      return 1;
411    }
412
413  if ((all_subdirs_mode && get_mode) ||
414      (all_subdirs_mode && set_mode) ||
415      (all_subdirs_mode && unset_mode))
416    {
417      fprintf(stderr, _("Can't use --all-dirs with --get or --set\n"));
418      return 1;
419    }
420
421  if ((recursive_list && get_mode) ||
422      (recursive_list && set_mode) ||
423      (recursive_list && unset_mode) ||
424      (recursive_list && all_entries_mode) ||
425      (recursive_list && all_subdirs_mode))
426    {
427      fprintf(stderr, _("--recursive-list should not be used with --get, --set, --unset, --all-entries, or --all-dirs\n"));
428      return 1;
429    }
430
431  if ((set_schema_mode && get_mode) ||
432      (set_schema_mode && set_mode) ||
433      (set_schema_mode && unset_mode) ||
434      (set_schema_mode && all_entries_mode) ||
435      (set_schema_mode && all_subdirs_mode))
436    {
437      fprintf(stderr, _("--set_schema should not be used with --get, --set, --unset, --all-entries, --all-dirs\n"));
438      return 1;
439    } 
440
441  if ((value_type != NULL) && !(set_mode || set_schema_mode))
442    {
443      fprintf(stderr, _("Value type is only relevant when setting a value\n"));
444      return 1;
445    }
446
447  if (set_mode && (value_type == NULL))
448    {
449      fprintf(stderr, _("Must specify a type when setting a value\n"));
450      return 1;
451    }
452
453  if (ping_gconfd && (shutdown_gconfd || set_mode || get_mode || unset_mode ||
454                      all_subdirs_mode || all_entries_mode || recursive_list ||
455                      spawn_gconfd || dir_exists || schema_file || makefile_install_mode ||
456                      break_key_mode || break_dir_mode || short_docs_mode ||
457                         long_docs_mode || schema_name_mode))
458    {
459      fprintf(stderr, _("Ping option must be used by itself.\n"));
460      return 1;
461    }
462
463  if (dir_exists && (shutdown_gconfd || set_mode || get_mode || unset_mode ||
464                     all_subdirs_mode || all_entries_mode || recursive_list ||
465                     spawn_gconfd || schema_file || makefile_install_mode ||
466                     break_key_mode || break_dir_mode || short_docs_mode ||
467                         long_docs_mode || schema_name_mode))
468    {
469      fprintf(stderr, _("--dir-exists option must be used by itself.\n"));
470      return 1;
471    }
472
473  if (schema_file && (shutdown_gconfd || set_mode || get_mode || unset_mode ||
474                      all_subdirs_mode || all_entries_mode || recursive_list ||
475                      spawn_gconfd || dir_exists || makefile_install_mode ||
476                      break_key_mode || break_dir_mode || short_docs_mode ||
477                         long_docs_mode || schema_name_mode))
478    {
479      fprintf(stderr, _("--install-schema-file must be used by itself.\n"));
480      return 1;
481    }
482
483
484  if (makefile_install_mode && (shutdown_gconfd || set_mode || get_mode || unset_mode ||
485                                all_subdirs_mode || all_entries_mode || recursive_list ||
486                                spawn_gconfd || dir_exists || schema_file ||
487                                break_key_mode || break_dir_mode || short_docs_mode ||
488                         long_docs_mode || schema_name_mode))
489    {
490      fprintf(stderr, _("--makefile-install-rule must be used by itself.\n"));
491      return 1;
492    }
493
494
495  if (break_key_mode && (shutdown_gconfd || set_mode || get_mode || unset_mode ||
496                                all_subdirs_mode || all_entries_mode || recursive_list ||
497                                spawn_gconfd || dir_exists || schema_file ||
498                                makefile_install_mode || break_dir_mode || short_docs_mode ||
499                         long_docs_mode || schema_name_mode))
500    {
501      fprintf(stderr, _("--break-key must be used by itself.\n"));
502      return 1;
503    }
504
505 
506  if (break_dir_mode && (shutdown_gconfd || set_mode || get_mode || unset_mode ||
507                                all_subdirs_mode || all_entries_mode || recursive_list ||
508                                spawn_gconfd || dir_exists || schema_file ||
509                                break_key_mode || makefile_install_mode || short_docs_mode ||
510                         long_docs_mode || schema_name_mode))
511    {
512      fprintf(stderr, _("--break-directory must be used by itself.\n"));
513      return 1;
514    }
515
516 
517  if (use_local_source && config_source == NULL)
518    {
519      fprintf(stderr, _("You must specify a config source with --config-source when using --direct\n"));
520      return 1;
521    }
522
523  if (config_source && !use_local_source)
524    {
525      fprintf (stderr, _("You should use --direct when using a non-default configuration source\n"));
526      return 1;
527    }
528 
529  if (!gconf_init(argc, argv, &err))
530    {
531      fprintf(stderr, _("Failed to init GConf: %s\n"), err->message);
532      g_error_free(err);
533      err = NULL;
534      return 1;
535    }
536
537  /* Do this first, since we want to do only this if the user selected
538     it. */
539  if (ping_gconfd)
540    {
541      if (gconf_ping_daemon())
542        return 0;
543      else
544        return 2;
545    }
546
547  /* Before creating engine */
548  if (default_source_mode)
549    {
550      const gchar** args = poptGetArgs(ctx);
551      if (do_get_default_source (conf, args)  == 1)
552        return 1;
553      else
554        return 0;
555    }
556 
557  if (makefile_install_mode)
558    {
559      g_assert (config_source == NULL);
560
561      /* Try the environment variable */
562      config_source = g_getenv("GCONF_CONFIG_SOURCE");
563
564      if (config_source == NULL)
565        {
566          fprintf(stderr, _("Must set the GCONF_CONFIG_SOURCE environment variable\n"));
567          return 1;
568        }
569
570      if (*config_source == '\0')
571        {
572          /* Properly set, but set to nothing (use default source) */
573          config_source = NULL;
574        }
575
576      use_local_source = TRUE;
577
578      /* shut down daemon, this is a race condition, but will usually work. */
579      gconf_shutdown_daemon (NULL);
580    }
581 
582  if (config_source == NULL)
583    conf = gconf_engine_get_default();
584  else
585    {
586      if (use_local_source)
587        conf = gconf_engine_get_local(config_source, &err);
588      else
589        conf = gconf_engine_get_for_address(config_source, &err);
590    }
591 
592  if (conf == NULL)
593    {
594      g_assert(err != NULL);
595      fprintf(stderr, _("Failed to access configuration source(s): %s\n"), err->message);
596      g_error_free(err);
597      err = NULL;
598      return 1;
599    }
600  else
601    {
602      g_assert(err == NULL);
603    }
604 
605  g_assert(conf != NULL);
606 
607  if (dir_exists != NULL)
608    {
609      gboolean success;
610
611      success = do_dir_exists(conf, dir_exists);
612
613      gconf_engine_unref(conf);
614     
615      if (success)
616        return 0; /* TRUE */
617      else
618        return 2; /* FALSE */
619    }
620
621  if (schema_file != NULL)
622    {
623      gint retval;
624
625      retval = do_load_schema_file(conf, schema_file);
626
627      gconf_engine_unref(conf);
628
629      return retval;
630    }
631 
632  if (spawn_gconfd)
633    {
634      do_spawn_daemon(conf);
635      /* don't exit, it's OK to have this along with other options
636         (however, it's probably pointless) */
637    }
638
639  if (makefile_install_mode)
640    {
641      const gchar** args = poptGetArgs(ctx);
642      gint retval = do_makefile_install(conf, args);
643
644      gconf_engine_unref(conf);
645
646      return retval;
647    }
648
649  if (break_key_mode)
650    {
651      const gchar** args = poptGetArgs(ctx);
652      gint retval = do_break_key(conf, args);
653
654      gconf_engine_unref(conf);
655
656      return retval;
657    }
658 
659  if (break_dir_mode)
660    {
661      const gchar** args = poptGetArgs(ctx);
662      gint retval = do_break_directory(conf, args);
663
664      gconf_engine_unref(conf);
665
666      return retval;
667    }
668 
669  if (get_mode)
670    {
671      const gchar** args = poptGetArgs(ctx);
672      if (do_get(conf, args)  == 1)
673        {
674          gconf_engine_unref(conf);
675          return 1;
676        }
677    }
678
679 
680  if (set_mode)
681    {
682      const gchar** args = poptGetArgs(ctx);
683      if (do_set(conf, args) == 1)
684        {
685          gconf_engine_unref(conf);
686          return 1;
687        }
688    }
689
690  if (set_schema_mode)
691    {
692      const gchar** args = poptGetArgs(ctx);
693      if (do_set_schema(conf, args) == 1)
694        {
695          gconf_engine_unref(conf);
696          return 1;
697        }
698    }
699
700  if (short_docs_mode)
701    {
702      const gchar** args = poptGetArgs(ctx);
703      if (do_short_docs(conf, args)  == 1)
704        {
705          gconf_engine_unref(conf);
706          return 1;
707        }
708    }
709
710  if (long_docs_mode)
711    {
712      const gchar** args = poptGetArgs(ctx);
713      if (do_long_docs(conf, args)  == 1)
714        {
715          gconf_engine_unref(conf);
716          return 1;
717        }
718    }
719
720  if (schema_name_mode)
721    {
722      const gchar** args = poptGetArgs(ctx);
723      if (do_get_schema_name(conf, args)  == 1)
724        {
725          gconf_engine_unref(conf);
726          return 1;
727        }
728    }
729
730  if (associate_schema_mode)
731    {
732      const gchar** args = poptGetArgs(ctx);
733      if (do_associate_schema(conf, args)  == 1)
734        {
735          gconf_engine_unref(conf);
736          return 1;
737        }
738    }
739 
740  if (all_entries_mode)
741    {
742      const gchar** args = poptGetArgs(ctx);
743
744      if (do_all_entries(conf, args) == 1)
745        {
746          gconf_engine_unref(conf);
747          return 1;
748        }
749    }
750
751  if (unset_mode)
752    {
753      const gchar** args = poptGetArgs(ctx);
754
755      if (do_unset(conf, args) == 1)
756        {
757          gconf_engine_unref(conf);
758          return 1;
759        }
760    }
761
762  if (all_subdirs_mode)
763    {
764      const gchar** args = poptGetArgs(ctx);
765
766      if (do_all_subdirs(conf, args) == 1)
767        {
768          gconf_engine_unref(conf);
769          return 1;
770        }
771    }
772
773  if (recursive_list)
774    {
775      const gchar** args = poptGetArgs(ctx);
776     
777      if (do_recursive_list(conf, args) == 1)
778        {
779          gconf_engine_unref(conf);
780          return 1;
781        }
782    }
783
784  poptFreeContext(ctx);
785
786  gconf_engine_unref(conf);
787
788  if (shutdown_gconfd)
789    {
790      err = NULL;
791      gconf_shutdown_daemon(&err);
792    }
793     
794  if (err != NULL)
795    {
796      fprintf(stderr, _("Shutdown error: %s\n"),
797              err->message);
798      g_error_free(err);
799      err = NULL;
800    }
801
802  return 0;
803}
804
805static void
806recurse_subdir_list(GConfEngine* conf, GSList* subdirs, const gchar* parent, guint depth)
807{
808  GSList* tmp;
809  gchar* whitespace;
810
811  whitespace = g_strnfill(depth, ' ');
812
813  tmp = subdirs;
814 
815  while (tmp != NULL)
816    {
817      gchar* s = tmp->data;
818     
819      printf("%s%s:\n", whitespace, s);
820     
821      list_pairs_in_dir(conf, s, depth);
822
823      recurse_subdir_list(conf, gconf_engine_all_dirs(conf, s, NULL), s, depth+1);
824
825      g_free(s);
826     
827      tmp = g_slist_next(tmp);
828    }
829 
830  g_slist_free(subdirs);
831  g_free(whitespace);
832}
833
834static int
835do_recursive_list(GConfEngine* conf, const gchar** args)
836{
837  if (args == NULL)
838    {
839      fprintf(stderr, _("Must specify one or more dirs to recursively list.\n"));
840      return 1;
841    }
842
843  while (*args)
844    {
845      GSList* subdirs;
846
847      subdirs = gconf_engine_all_dirs(conf, *args, NULL);
848
849      list_pairs_in_dir(conf, *args, 0);
850         
851      recurse_subdir_list(conf, subdirs, *args, 1);
852 
853      ++args;
854    }
855
856  return 0;
857}
858
859static void
860list_pairs_in_dir(GConfEngine* conf, const gchar* dir, guint depth)
861{
862  GSList* pairs;
863  GSList* tmp;
864  gchar* whitespace;
865  GError* err = NULL;
866 
867  whitespace = g_strnfill(depth, ' ');
868
869  pairs = gconf_engine_all_entries(conf, dir, &err);
870         
871  if (err != NULL)
872    {
873      fprintf(stderr, _("Failure listing entries in `%s': %s\n"),
874              dir, err->message);
875      g_error_free(err);
876      err = NULL;
877    }
878
879  if (pairs != NULL)
880    {
881      tmp = pairs;
882
883      while (tmp != NULL)
884        {
885          GConfEntry* pair = tmp->data;
886          gchar* s;
887
888          if (pair->value)
889                  s = gconf_value_to_string(pair->value);
890          else
891                  s = g_strdup(_("(no value set)"));
892         
893          printf(" %s%s = %s\n", whitespace,
894                 gconf_key_key (gconf_entry_get_key (pair)),
895                 s);
896
897          g_free(s);
898                 
899          gconf_entry_free(pair);
900
901          tmp = g_slist_next(tmp);
902        }
903
904      g_slist_free(pairs);
905    }
906
907  g_free(whitespace);
908}
909
910static int
911do_all_pairs(GConfEngine* conf, const gchar** args)
912{     
913  while (*args)
914    {
915      list_pairs_in_dir(conf, *args, 0);
916      ++args;
917    }
918  return 0;
919}
920
921static gboolean
922do_dir_exists(GConfEngine* conf, const gchar* dir)
923{
924  GError* err = NULL;
925  gboolean exists = FALSE;
926 
927  exists = gconf_engine_dir_exists(conf, dir_exists, &err);
928 
929  if (err != NULL)
930    {
931      fprintf(stderr, "%s\n", err->message);
932      g_error_free(err);
933      err = NULL;
934    }
935 
936  return exists;
937}
938
939static void
940do_spawn_daemon(GConfEngine* conf)
941{
942  GError* err = NULL;
943
944  if (!gconf_spawn_daemon(&err))
945    {
946      fprintf(stderr, _("Failed to spawn the config server (gconfd): %s\n"),
947              err->message);
948      g_error_free(err);
949      err = NULL;
950    }
951}
952
953static int
954do_get(GConfEngine* conf, const gchar** args)
955{
956  GError* err = NULL;
957
958  if (args == NULL)
959    {
960      fprintf(stderr, _("Must specify a key or keys to get\n"));
961      return 1;
962    }
963     
964  while (*args)
965    {
966      GConfValue* value;
967      gchar* s;
968
969      err = NULL;
970
971      value = gconf_engine_get (conf, *args, &err);
972         
973      if (value != NULL)
974        {
975          if (value->type != GCONF_VALUE_SCHEMA)
976            {
977              s = gconf_value_to_string(value);
978
979              printf("%s\n", s);
980
981              g_free(s);
982            }
983          else
984            {
985              GConfSchema* sc = gconf_value_get_schema(value);
986              GConfValueType stype = gconf_schema_get_type(sc);
987              GConfValueType slist_type = gconf_schema_get_list_type(sc);
988              GConfValueType scar_type = gconf_schema_get_car_type(sc);
989              GConfValueType scdr_type = gconf_schema_get_cdr_type(sc);
990              const gchar* long_desc = gconf_schema_get_long_desc(sc);
991              const gchar* short_desc = gconf_schema_get_short_desc(sc);
992              const gchar* owner = gconf_schema_get_owner(sc);
993              GConfValue* def_value = gconf_schema_get_default_value(sc);
994             
995              printf(_("Type: %s\n"), gconf_value_type_to_string(stype));
996              printf(_("List Type: %s\n"), gconf_value_type_to_string(slist_type));
997              printf(_("Car Type: %s\n"), gconf_value_type_to_string(scar_type));
998              printf(_("Cdr Type: %s\n"), gconf_value_type_to_string(scdr_type));
999              if (def_value)
1000                s = gconf_value_to_string (def_value);
1001              else
1002                s = NULL;
1003              printf(_("Default Value: %s\n"), def_value ? s : _("Unset"));
1004              g_free (s);
1005              printf(_("Owner: %s\n"), owner ? owner : _("Unset"));
1006              printf(_("Short Desc: %s\n"), short_desc ? short_desc : _("Unset"));
1007              printf(_("Long Desc: %s\n"), long_desc ? long_desc : _("Unset"));
1008            }
1009
1010          gconf_value_free(value);
1011        }
1012      else
1013        {
1014          if (err == NULL)
1015            {
1016              fprintf(stderr, _("No value set for `%s'\n"), *args);
1017            }
1018          else
1019            {
1020              fprintf(stderr, _("Failed to get value for `%s': %s\n"),
1021                      *args, err->message);
1022              g_error_free(err);
1023              err = NULL;
1024            }
1025        }
1026 
1027      ++args;
1028    }
1029  return 0;
1030}
1031
1032static GConfValueType
1033read_value_type(const char *string)
1034{
1035  GConfValueType type = GCONF_VALUE_INVALID;
1036  switch (*string)
1037    {
1038    case 'i':
1039    case 'I':
1040      type = GCONF_VALUE_INT;
1041      break;
1042    case 'f':
1043    case 'F':
1044      type = GCONF_VALUE_FLOAT;
1045      break;
1046    case 'b':
1047    case 'B':
1048      type = GCONF_VALUE_BOOL;
1049      break;
1050    case 's':
1051    case 'S':
1052      switch (value_type[1])
1053        {
1054        case 't':
1055        case 'T':
1056          type = GCONF_VALUE_STRING;
1057          break;
1058        case 'c':
1059        case 'C':
1060          type = GCONF_VALUE_SCHEMA;
1061          break;
1062        default:
1063          fprintf(stderr, _("Don't understand type `%s'\n"), value_type);
1064        }
1065      break;
1066    case 'l':
1067    case 'L':
1068      type = GCONF_VALUE_LIST;
1069      break;
1070    case 'p':
1071    case 'P':
1072      type = GCONF_VALUE_PAIR;
1073      break;
1074    default:
1075      fprintf(stderr, _("Don't understand type `%s'\n"), value_type);
1076    }
1077  return type;
1078}
1079
1080static int
1081do_set(GConfEngine* conf, const gchar** args)
1082{
1083  GError* err = NULL;
1084 
1085  if (args == NULL)
1086    {
1087      fprintf(stderr, _("Must specify alternating keys/values as arguments\n"));
1088      return 1;
1089    }
1090
1091  while (*args)
1092    {
1093      const gchar* key;
1094      const gchar* value;
1095      GConfValueType type = GCONF_VALUE_INVALID;
1096      GConfValueType list_type = GCONF_VALUE_INVALID;
1097      GConfValueType car_type = GCONF_VALUE_INVALID;
1098      GConfValueType cdr_type = GCONF_VALUE_INVALID;
1099      GConfValue* gval;
1100
1101      key = *args;
1102      ++args;
1103      value = *args;
1104
1105      if (value == NULL)
1106        {
1107          fprintf(stderr, _("No value to set for key: `%s'\n"), key);
1108          return 1;
1109        }
1110
1111      type = read_value_type(value_type);
1112      if (type == GCONF_VALUE_INVALID)
1113        return 1;
1114      if (value_list_type != NULL)
1115        {
1116          list_type = read_value_type(value_list_type);
1117          if (list_type == GCONF_VALUE_INVALID)
1118            return 1;
1119        }
1120      if (value_car_type != NULL)
1121        {
1122          car_type = read_value_type(value_car_type);
1123          if (car_type == GCONF_VALUE_INVALID)
1124            return 1;
1125        }
1126      if (value_cdr_type != NULL)
1127        {
1128          cdr_type = read_value_type(value_cdr_type);
1129          if (cdr_type == GCONF_VALUE_INVALID)
1130            return 1;
1131        }
1132
1133      if (type == GCONF_VALUE_SCHEMA)
1134        {
1135          fprintf(stderr, _("Cannot set schema as value\n"));
1136          return 1;
1137        }
1138
1139      if (type == GCONF_VALUE_LIST &&
1140          list_type != GCONF_VALUE_STRING &&
1141          list_type != GCONF_VALUE_INT &&
1142          list_type != GCONF_VALUE_FLOAT &&
1143          list_type != GCONF_VALUE_BOOL)
1144        {
1145          fprintf(stderr, _("When setting a list you must specify a primitive list-type\n"));
1146          return 1;
1147        }
1148
1149      if (type == GCONF_VALUE_PAIR &&
1150          ((car_type != GCONF_VALUE_STRING &&
1151            car_type != GCONF_VALUE_INT &&
1152            car_type != GCONF_VALUE_FLOAT &&
1153            car_type != GCONF_VALUE_BOOL) ||
1154           (cdr_type != GCONF_VALUE_STRING &&
1155            cdr_type != GCONF_VALUE_INT &&
1156            cdr_type != GCONF_VALUE_FLOAT &&
1157            cdr_type != GCONF_VALUE_BOOL)))
1158        {
1159          fprintf(stderr, _("When setting a pair you must specify a primitive car-type and cdr-type\n"));
1160          return 1;
1161        }
1162
1163      err = NULL;
1164
1165      if (type == GCONF_VALUE_LIST)
1166        gval = gconf_value_new_list_from_string(list_type, value, &err);
1167      else if (type == GCONF_VALUE_PAIR)
1168        gval = gconf_value_new_pair_from_string(car_type, cdr_type, value, &err);
1169      else
1170        gval = gconf_value_new_from_string(type, value, &err);
1171
1172      if (gval == NULL)
1173        {
1174          fprintf(stderr, _("Error: %s\n"),
1175                  err->message);
1176          g_error_free(err);
1177          err = NULL;
1178          return 1;
1179        }
1180
1181      err = NULL;
1182         
1183      gconf_engine_set (conf, key, gval, &err);
1184
1185      if (err != NULL)
1186        {
1187          fprintf(stderr, _("Error setting value: %s\n"),
1188                  err->message);
1189          g_error_free(err);
1190          err = NULL;
1191          return 1;
1192        }
1193
1194      gconf_value_free(gval);
1195
1196      ++args;
1197    }
1198
1199  err = NULL;
1200
1201  gconf_engine_suggest_sync(conf, &err);
1202
1203  if (err != NULL)
1204    {
1205      fprintf(stderr, _("Error syncing: %s\n"),
1206              err->message);
1207      return 1;
1208    }
1209
1210  return 0;
1211}
1212
1213enum
1214{
1215  SCHEMA_INFO_SHORT_DOCS,
1216  SCHEMA_INFO_LONG_DOCS,
1217  SCHEMA_INFO_SCHEMA_NAME
1218};
1219
1220static int
1221do_schema_info (GConfEngine *conf, const gchar **args,
1222                int info)
1223{
1224  GError* err = NULL;
1225
1226  if (args == NULL)
1227    {
1228      fprintf (stderr, _("Must specify a key or keys on the command line\n"));
1229      return 1;
1230    }
1231     
1232  while (*args)
1233    {
1234      GConfEntry* entry;
1235
1236      err = NULL;
1237
1238      entry = gconf_engine_get_entry (conf, *args, NULL, TRUE, &err);
1239
1240      if (entry != NULL)
1241        {
1242          const char *s;
1243         
1244          s = gconf_entry_get_schema_name (entry);
1245
1246          if (s == NULL)
1247            {
1248              fprintf (stderr, _("No schema known for `%s'\n"), *args);
1249            }
1250          else if (info == SCHEMA_INFO_SCHEMA_NAME)
1251            {
1252              printf ("%s\n", s);
1253            }
1254          else
1255            {
1256              GConfValue *val;
1257
1258              err = NULL;
1259             
1260              val = gconf_engine_get (conf, s, &err);
1261
1262              if (val != NULL && val->type == GCONF_VALUE_SCHEMA)
1263                {
1264                  GConfSchema *schema;
1265                  const char *docs;
1266
1267                  docs = NULL;
1268                  schema = gconf_value_get_schema (val);
1269
1270                  if (schema)
1271                    {
1272                      if (info == SCHEMA_INFO_SHORT_DOCS)
1273                        docs = gconf_schema_get_short_desc (schema);
1274                      else if (info == SCHEMA_INFO_LONG_DOCS)
1275                        docs = gconf_schema_get_long_desc (schema);
1276                    }
1277                 
1278                  if (docs)
1279                    printf ("%s\n", docs);
1280                  else
1281                    fprintf (stderr, _("No doc string stored in schema at '%s'\n"),
1282                             s);
1283                }
1284              else if (err != NULL)
1285                {
1286                  fprintf (stderr, _("Error getting schema at '%s': %s\n"),
1287                           s, err->message);
1288                  g_error_free (err);
1289                }
1290              else
1291                {
1292                  if (val == NULL)
1293                    fprintf (stderr, _("No schema stored at '%s'\n"),
1294                             s);
1295                  else
1296                    fprintf (stderr, _("Value at '%s' is not a schema\n"),
1297                             s);
1298                }
1299
1300              if (val)
1301                gconf_value_free (val);
1302            }
1303         
1304          gconf_entry_free (entry);
1305        }
1306      else
1307        {
1308          if (err == NULL)
1309            {
1310              fprintf(stderr, _("No value set for `%s'\n"), *args);
1311            }
1312          else
1313            {
1314              fprintf(stderr, _("Failed to get value for `%s': %s\n"),
1315                      *args, err->message);
1316              g_error_free(err);
1317              err = NULL;
1318            }
1319        }
1320 
1321      ++args;
1322    }
1323 
1324  return 0;
1325}
1326
1327static int
1328do_short_docs (GConfEngine *conf, const gchar **args)
1329{
1330  return do_schema_info (conf, args, SCHEMA_INFO_SHORT_DOCS);
1331}
1332
1333static int
1334do_long_docs (GConfEngine *conf, const gchar **args)
1335{
1336  return do_schema_info (conf, args, SCHEMA_INFO_LONG_DOCS);
1337}
1338
1339static int
1340do_get_schema_name (GConfEngine *conf, const gchar **args)
1341{
1342  return do_schema_info (conf, args, SCHEMA_INFO_SCHEMA_NAME);
1343}
1344
1345static int
1346do_associate_schema (GConfEngine *conf, const gchar **args)
1347{
1348  GError *err;
1349 
1350  if (args[0] == NULL || args[1] == NULL || args[2] != NULL)
1351    {
1352      fprintf (stderr, _("Must specify a schema name followed by the key name to apply it to\n"));
1353      return 1;
1354    }
1355
1356  err = NULL;
1357  if (!gconf_engine_associate_schema (conf, args[1], args[0], &err))
1358    {
1359      fprintf (stderr, _("Error associating schema name '%s' with key name '%s': %s\n"),
1360               args[0], args[1], err->message);
1361      g_error_free (err);
1362
1363      return 1;
1364    }
1365
1366  return 0;
1367}
1368
1369static int
1370do_set_schema(GConfEngine* conf, const gchar** args)
1371{
1372  GConfSchema* sc;
1373  GConfValue* val;
1374  const gchar* key;
1375  GError* err = NULL;
1376 
1377  if ((args == NULL) || (args[1] != NULL))
1378    {
1379      fprintf(stderr, _("Must specify key (schema name) as the only argument\n"));
1380      return 1;
1381    }
1382     
1383  key = *args;
1384
1385  val = gconf_value_new(GCONF_VALUE_SCHEMA);
1386
1387  sc = gconf_schema_new();
1388
1389  gconf_value_set_schema_nocopy(val, sc);
1390
1391  if (short_desc)
1392    gconf_schema_set_short_desc(sc, short_desc);
1393
1394  if (long_desc)
1395    gconf_schema_set_long_desc(sc, long_desc);
1396
1397  if (owner)
1398    gconf_schema_set_owner(sc, owner);
1399
1400  if (value_type)
1401    {
1402      GConfValueType type = GCONF_VALUE_INVALID;
1403
1404      type = read_value_type(value_type);
1405
1406      if (type != GCONF_VALUE_INVALID)
1407        gconf_schema_set_type(sc, type);
1408    }
1409
1410  if (value_list_type)
1411    {
1412      GConfValueType type = GCONF_VALUE_INVALID;
1413
1414      type = read_value_type(value_list_type);
1415
1416      if (type != GCONF_VALUE_STRING &&
1417          type != GCONF_VALUE_INT &&
1418          type != GCONF_VALUE_FLOAT &&
1419          type != GCONF_VALUE_BOOL)
1420        {
1421          fprintf(stderr, _("List type must be a primitive type: string, int, float or bool\n"));
1422          return 1;
1423
1424        }
1425
1426      if (type != GCONF_VALUE_INVALID)
1427        gconf_schema_set_list_type(sc, type);
1428    }
1429
1430  if (value_car_type)
1431    {
1432      GConfValueType type = GCONF_VALUE_INVALID;
1433
1434      type = read_value_type(value_car_type);
1435
1436      if (type != GCONF_VALUE_STRING &&
1437          type != GCONF_VALUE_INT &&
1438          type != GCONF_VALUE_FLOAT &&
1439          type != GCONF_VALUE_BOOL)
1440        {
1441          fprintf(stderr, _("Pair car type must be a primitive type: string, int, float or bool\n"));
1442          return 1;
1443
1444        }
1445
1446      if (type != GCONF_VALUE_INVALID)
1447        gconf_schema_set_car_type(sc, type);
1448    }
1449
1450  if (value_cdr_type)
1451    {
1452      GConfValueType type = GCONF_VALUE_INVALID;
1453
1454      type = read_value_type(value_cdr_type);
1455
1456      if (type != GCONF_VALUE_STRING &&
1457          type != GCONF_VALUE_INT &&
1458          type != GCONF_VALUE_FLOAT &&
1459          type != GCONF_VALUE_BOOL)
1460        {
1461          fprintf(stderr, _("Pair cdr type must be a primitive type: string, int, float or bool\n"));
1462          return 1;
1463
1464        }
1465
1466      if (type != GCONF_VALUE_INVALID)
1467        gconf_schema_set_cdr_type(sc, type);
1468    }
1469
1470  err = NULL;
1471     
1472  gconf_engine_set (conf, key, val, &err);
1473     
1474  if (err != NULL)
1475    {
1476      fprintf(stderr, _("Error setting value: %s"),
1477              err->message);
1478      g_error_free(err);
1479      err = NULL;
1480      return 1;
1481    }
1482     
1483  gconf_value_free(val);
1484
1485  err = NULL;
1486  gconf_engine_suggest_sync(conf, &err);
1487     
1488  if (err != NULL)
1489    {
1490      fprintf(stderr, _("Error syncing: %s"),
1491              err->message);
1492      g_error_free(err);
1493      err = NULL;
1494      return 1;
1495    }
1496
1497  return 0;
1498}
1499
1500static int
1501do_all_entries(GConfEngine* conf, const gchar** args)
1502{
1503  if (args == NULL)
1504    {
1505      fprintf(stderr, _("Must specify one or more dirs to get key/value pairs from.\n"));
1506      return 1;
1507    }
1508 
1509  return do_all_pairs(conf, args);
1510}
1511
1512static int
1513do_unset(GConfEngine* conf, const gchar** args)
1514{
1515  GError* err = NULL;
1516 
1517  if (args == NULL)
1518    {
1519      fprintf(stderr, _("Must specify one or more keys to unset.\n"));
1520      return 1;
1521    }
1522
1523  while (*args)
1524    {
1525      err = NULL;
1526      gconf_engine_unset(conf, *args, &err);
1527
1528      if (err != NULL)
1529        {
1530          fprintf(stderr, _("Error unsetting `%s': %s\n"),
1531                  *args, err->message);
1532          g_error_free(err);
1533          err = NULL;
1534        }
1535
1536      ++args;
1537    }
1538
1539  err = NULL;
1540  gconf_engine_suggest_sync(conf, NULL); /* ignore errors */
1541
1542  return 0;
1543}
1544
1545
1546static int
1547do_all_subdirs(GConfEngine* conf, const gchar** args)
1548{
1549  GError* err = NULL;
1550 
1551  if (args == NULL)
1552    {
1553      fprintf(stderr, _("Must specify one or more dirs to get subdirs from.\n"));
1554      return 1;
1555    }
1556     
1557  while (*args)
1558    {
1559      GSList* subdirs;
1560      GSList* tmp;
1561
1562      err = NULL;
1563
1564      subdirs = gconf_engine_all_dirs(conf, *args, &err);
1565         
1566      if (subdirs != NULL)
1567        {
1568          tmp = subdirs;
1569
1570          while (tmp != NULL)
1571            {
1572              gchar* s = tmp->data;
1573
1574              printf(" %s\n", s);
1575
1576              g_free(s);
1577
1578              tmp = g_slist_next(tmp);
1579            }
1580
1581          g_slist_free(subdirs);
1582        }
1583      else
1584        {
1585          if (err != NULL)
1586            {
1587              fprintf(stderr, _("Error listing dirs: %s\n"),
1588                      err->message);
1589              g_error_free(err);
1590              err = NULL;
1591            }
1592        }
1593 
1594      ++args;
1595    }
1596
1597  return 0;
1598}
1599
1600/*
1601 * Schema stuff
1602 */
1603
1604typedef struct _SchemaInfo SchemaInfo;
1605
1606struct _SchemaInfo {
1607  gchar* key;
1608  gchar* owner;
1609  GSList* apply_to;
1610  GConfValueType type;
1611  GConfValueType list_type;
1612  GConfValueType car_type;
1613  GConfValueType cdr_type;
1614  GConfValue* global_default;
1615  GHashTable* hash;
1616  GConfEngine* conf;
1617};
1618
1619static int
1620fill_default_from_string(SchemaInfo* info, const gchar* default_value,
1621                         GConfValue** retloc)
1622{
1623  g_return_val_if_fail(info->key != NULL, 1);
1624  g_return_val_if_fail(default_value != NULL, 1);
1625
1626  switch (info->type)
1627    {
1628    case GCONF_VALUE_INVALID:
1629      fprintf(stderr, _("WARNING: invalid or missing type for schema (%s)\n"),
1630              info->key);
1631      break;
1632
1633    case GCONF_VALUE_LIST:
1634      {
1635        GError* error = NULL;
1636        if (info->list_type == GCONF_VALUE_INVALID)
1637          {
1638            fprintf(stderr, _("WARNING: invalid or missing list_type for schema (%s)\n"),
1639                    info->key);
1640            break;
1641          }
1642        *retloc = gconf_value_new_list_from_string(info->list_type,
1643                                                   default_value,
1644                                                   &error);
1645        if (*retloc == NULL)
1646          {
1647            g_assert(error != NULL);
1648
1649            fprintf(stderr, _("WARNING: Failed to parse default value `%s' for schema (%s)\n"), default_value, info->key);
1650
1651            g_error_free(error);
1652            error = NULL;
1653          }
1654        else
1655          {
1656            g_assert(error == NULL);
1657          }
1658      }
1659      break;
1660
1661    case GCONF_VALUE_PAIR:
1662      {
1663        GError* error = NULL;
1664        if (info->car_type == GCONF_VALUE_INVALID ||
1665            info->cdr_type == GCONF_VALUE_INVALID)
1666          {
1667            fprintf(stderr, _("WARNING: invalid or missing car_type or cdr_type for schema (%s)\n"),
1668                    info->key);
1669            break;
1670          }
1671        *retloc = gconf_value_new_pair_from_string(info->car_type,
1672                                                   info->cdr_type,
1673                                                   default_value,
1674                                                   &error);
1675        if (*retloc == NULL)
1676          {
1677            g_assert(error != NULL);
1678
1679            fprintf(stderr, _("WARNING: Failed to parse default value `%s' for schema (%s)\n"), default_value, info->key);
1680
1681            g_error_free(error);
1682            error = NULL;
1683          }
1684        else
1685          {
1686            g_assert(error == NULL);
1687          }
1688      }
1689      break;
1690
1691    case GCONF_VALUE_SCHEMA:
1692      fprintf(stderr, _("WARNING: You cannot set a default value for a schema\n"));
1693      break;
1694
1695    case GCONF_VALUE_STRING:
1696    case GCONF_VALUE_INT:
1697    case GCONF_VALUE_BOOL:
1698    case GCONF_VALUE_FLOAT:
1699      {
1700        GError* error = NULL;
1701        *retloc = gconf_value_new_from_string(info->type,
1702                                              default_value,
1703                                              &error);
1704        if (*retloc == NULL)
1705          {
1706            g_assert(error != NULL);
1707
1708            fprintf(stderr, _("WARNING: Failed to parse default value `%s' for schema (%s)\n"), default_value, info->key);
1709
1710            g_error_free(error);
1711            error = NULL;
1712          }
1713        else
1714          {
1715            g_assert(error == NULL);
1716          }
1717      }
1718      break;
1719     
1720    default:
1721      fprintf(stderr, _("WARNING: gconftool internal error, unknown GConfValueType\n"));
1722      break;
1723    }
1724
1725  return 0;
1726}
1727
1728static int
1729extract_global_info(xmlNodePtr node,
1730                    SchemaInfo* info)
1731{
1732  xmlNodePtr iter;
1733  char* default_value = NULL;
1734     
1735  iter = node->childs;
1736
1737  while (iter != NULL)
1738    {
1739      if (iter->type == XML_ELEMENT_NODE)
1740        {
1741          char* tmp;
1742     
1743          if (strcmp(iter->name, "key") == 0)
1744            {
1745              tmp = xmlNodeGetContent(iter);
1746              if (tmp)
1747                {
1748                  info->key = g_strdup(tmp);
1749                  xmlFree(tmp);
1750                }
1751            }
1752          else if (strcmp(iter->name, "owner") == 0)
1753            {
1754              tmp = xmlNodeGetContent(iter);
1755              if (tmp)
1756                {
1757                  info->owner = g_strdup(tmp);
1758                  xmlFree(tmp);
1759                }
1760            }
1761          else if (strcmp(iter->name, "type") == 0)
1762            {
1763              tmp = xmlNodeGetContent(iter);
1764              if (tmp)
1765                {
1766                  info->type = gconf_value_type_from_string(tmp);
1767                  if (info->type == GCONF_VALUE_INVALID)
1768                    fprintf(stderr, _("WARNING: failed to parse type name `%s'\n"),
1769                            tmp);
1770                  xmlFree(tmp);
1771                }
1772            }
1773          else if (strcmp(iter->name, "list_type") == 0)
1774            {
1775              tmp = xmlNodeGetContent(iter);
1776              if (tmp)
1777                {
1778                  info->list_type = gconf_value_type_from_string(tmp);
1779                  if (info->list_type != GCONF_VALUE_INT &&
1780                      info->list_type != GCONF_VALUE_FLOAT &&
1781                      info->list_type != GCONF_VALUE_STRING &&
1782                      info->list_type != GCONF_VALUE_BOOL)
1783                    {
1784                      info->list_type = GCONF_VALUE_INVALID;
1785                      fprintf(stderr, _("WARNING: list_type can only be int, float, string or bool and not `%s'\n"),
1786                              tmp);
1787                    }
1788                  else if (info->list_type == GCONF_VALUE_INVALID)
1789                    fprintf(stderr, _("WARNING: failed to parse type name `%s'\n"),
1790                            tmp);
1791                  xmlFree(tmp);
1792                }
1793            }
1794          else if (strcmp(iter->name, "car_type") == 0)
1795            {
1796              tmp = xmlNodeGetContent(iter);
1797              if (tmp)
1798                {
1799                  info->car_type = gconf_value_type_from_string(tmp);
1800                  if (info->car_type != GCONF_VALUE_INT &&
1801                      info->car_type != GCONF_VALUE_FLOAT &&
1802                      info->car_type != GCONF_VALUE_STRING &&
1803                      info->car_type != GCONF_VALUE_BOOL)
1804                    {
1805                      info->car_type = GCONF_VALUE_INVALID;
1806                      fprintf(stderr, _("WARNING: car_type can only be int, float, string or bool and not `%s'\n"),
1807                              tmp);
1808                    }
1809                  else if (info->car_type == GCONF_VALUE_INVALID)
1810                    fprintf(stderr, _("WARNING: failed to parse type name `%s'\n"),
1811                            tmp);
1812                  xmlFree(tmp);
1813                }
1814            }
1815          else if (strcmp(iter->name, "cdr_type") == 0)
1816            {
1817              tmp = xmlNodeGetContent(iter);
1818              if (tmp)
1819                {
1820                  info->cdr_type = gconf_value_type_from_string(tmp);
1821                  if (info->cdr_type != GCONF_VALUE_INT &&
1822                      info->cdr_type != GCONF_VALUE_FLOAT &&
1823                      info->cdr_type != GCONF_VALUE_STRING &&
1824                      info->cdr_type != GCONF_VALUE_BOOL)
1825                    {
1826                      info->cdr_type = GCONF_VALUE_INVALID;
1827                      fprintf(stderr, _("WARNING: cdr_type can only be int, float, string or bool and not `%s'\n"),
1828                              tmp);
1829                    }
1830                  else if (info->cdr_type == GCONF_VALUE_INVALID)
1831                    fprintf(stderr, _("WARNING: failed to parse type name `%s'\n"),
1832                            tmp);
1833                  xmlFree(tmp);
1834                }
1835            }
1836          else if (strcmp(iter->name, "default") == 0)
1837            {
1838              default_value = xmlNodeGetContent(iter);
1839            }
1840          else if (strcmp(iter->name, "locale") == 0)
1841            {
1842              ; /* ignore, this is parsed later after we have the global info */
1843            }
1844          else if (strcmp(iter->name, "applyto") == 0)
1845            {
1846              /* Add the contents to the list of nodes to apply to */
1847              tmp = xmlNodeGetContent(iter);
1848
1849              if (tmp)
1850                {
1851                  info->apply_to = g_slist_prepend(info->apply_to, g_strdup(tmp));
1852                  free(tmp);
1853                }
1854              else
1855                fprintf(stderr, _("WARNING: empty <applyto> node"));
1856            }
1857          else
1858            fprintf(stderr, _("WARNING: node <%s> not understood below <schema>\n"),
1859                    iter->name);
1860
1861        }
1862     
1863      iter = iter->next;
1864    }
1865
1866  if (info->key == NULL)
1867    {
1868      fprintf(stderr, _("WARNING: no key specified for schema\n"));
1869      if (default_value != NULL)
1870        free(default_value);
1871      return 1;
1872    }
1873
1874  g_assert(info->key != NULL);
1875 
1876  /* Have to do this last, because the type may come after the default
1877     value
1878  */
1879  if (default_value != NULL)
1880    {
1881      fill_default_from_string(info, default_value, &info->global_default);
1882
1883      free(default_value);
1884      default_value = NULL;
1885    }
1886
1887  return 0;
1888}
1889
1890static int
1891process_locale_info(xmlNodePtr node, SchemaInfo* info)
1892{
1893  char* name;
1894  GConfSchema* schema;
1895  xmlNodePtr iter;
1896 
1897  name = xmlGetProp(node, "name");
1898
1899  if (name == NULL)
1900    {
1901      fprintf(stderr, _("WARNING: <locale> node has no `name=\"locale\"' attribute, ignoring\n"));
1902      return 1;
1903    }
1904
1905  if (g_hash_table_lookup(info->hash, name) != NULL)
1906    {
1907      fprintf(stderr, _("WARNING: multiple <locale> nodes for locale `%s', ignoring all past first\n"),
1908              name);
1909      xmlFree(name);
1910      return 1;
1911    }
1912 
1913  schema = gconf_schema_new();
1914
1915  gconf_schema_set_locale(schema, name);
1916
1917  xmlFree(name);
1918
1919  /* Fill in the global info */
1920  if (info->global_default != NULL)
1921    gconf_schema_set_default_value(schema, info->global_default);
1922     
1923  if (info->type != GCONF_VALUE_INVALID)
1924    gconf_schema_set_type(schema, info->type);
1925
1926  if (info->list_type != GCONF_VALUE_INVALID)
1927    gconf_schema_set_list_type(schema, info->list_type);
1928
1929  if (info->car_type != GCONF_VALUE_INVALID)
1930    gconf_schema_set_car_type(schema, info->car_type);
1931
1932  if (info->cdr_type != GCONF_VALUE_INVALID)
1933    gconf_schema_set_cdr_type(schema, info->cdr_type);
1934
1935  if (info->owner != NULL)
1936    gconf_schema_set_owner(schema, info->owner);
1937
1938
1939  /* Locale-specific info */
1940  iter = node->childs;
1941 
1942  while (iter != NULL)
1943    {
1944      if (iter->type == XML_ELEMENT_NODE)
1945        {
1946          if (strcmp(iter->name, "default") == 0)
1947            {
1948              GConfValue* val = NULL;
1949              char* tmp;
1950
1951              tmp = xmlNodeGetContent(iter);
1952
1953              if (tmp != NULL)
1954                {
1955                  fill_default_from_string(info, tmp, &val);
1956                  if (val != NULL)
1957                    gconf_schema_set_default_value_nocopy(schema, val);
1958
1959                  xmlFree(tmp);
1960                }
1961            }
1962          else if (strcmp(iter->name, "short") == 0)
1963            {
1964              char* tmp;
1965
1966              tmp = xmlNodeGetContent(iter);
1967
1968              if (tmp != NULL)
1969                {
1970                  gconf_schema_set_short_desc(schema, tmp);
1971                  xmlFree(tmp);
1972                }
1973            }
1974          else if (strcmp(iter->name, "long") == 0)
1975            {
1976              char* tmp;
1977
1978              tmp = xmlNodeGetContent(iter);
1979
1980              if (tmp != NULL)
1981                {
1982                  gconf_schema_set_long_desc(schema, tmp);
1983                  xmlFree(tmp);
1984                }
1985            }
1986          else
1987            {
1988              fprintf(stderr, _("WARNING: Invalid node <%s> in a <locale> node\n"),
1989                      iter->name);
1990            }
1991        }
1992     
1993      iter = iter->next;
1994    }
1995
1996  g_hash_table_insert(info->hash,
1997                      (gchar*)gconf_schema_get_locale(schema), /* cheat to save copying this string */
1998                      schema);
1999
2000  return 0;
2001}
2002
2003static void
2004hash_foreach(gpointer key, gpointer value, gpointer user_data)
2005{
2006  SchemaInfo* info;
2007  GConfSchema* schema;
2008  GError* error = NULL;
2009 
2010  info = user_data;
2011  schema = value;
2012 
2013  if (!gconf_engine_set_schema(info->conf, info->key, schema, &error))
2014    {
2015      g_assert(error != NULL);
2016
2017      fprintf(stderr, _("WARNING: failed to install schema `%s' locale `%s': %s\n"),
2018              info->key, gconf_schema_get_locale(schema), error->message);
2019      g_error_free(error);
2020      error = NULL;
2021    }
2022  else
2023    {
2024      g_assert(error == NULL);
2025      printf(_("Installed schema `%s' for locale `%s'\n"),
2026             info->key, gconf_schema_get_locale(schema));
2027    }
2028     
2029  gconf_schema_free(schema);
2030}
2031
2032
2033static int
2034process_key_list(GConfEngine* conf, const gchar* schema_name, GSList* keylist)
2035{
2036  GSList* tmp;
2037  GError* error = NULL;
2038
2039  tmp = keylist;
2040
2041  while (tmp != NULL)
2042    {
2043      if (!gconf_engine_associate_schema(conf, tmp->data, schema_name,  &error))
2044        {
2045          g_assert(error != NULL);
2046         
2047          fprintf(stderr, _("WARNING: failed to associate schema `%s' with key `%s': %s\n"),
2048                  schema_name, (gchar*)tmp->data, error->message);
2049          g_error_free(error);
2050          error = NULL;
2051        }
2052      else
2053        {
2054          g_assert(error == NULL);
2055          printf(_("Attached schema `%s' to key `%s'\n"),
2056                 schema_name, (gchar*)tmp->data);
2057        }
2058         
2059      tmp = g_slist_next(tmp);
2060    }
2061 
2062  return 0;
2063}
2064
2065static int
2066process_schema(GConfEngine* conf, xmlNodePtr node)
2067{
2068  xmlNodePtr iter;
2069  SchemaInfo info;
2070
2071  info.key = NULL;
2072  info.type = GCONF_VALUE_INVALID;
2073  info.list_type = GCONF_VALUE_INVALID;
2074  info.car_type = GCONF_VALUE_INVALID;
2075  info.cdr_type = GCONF_VALUE_INVALID;
2076  info.apply_to = NULL;
2077  info.owner = NULL;
2078  info.global_default = NULL;
2079  info.hash = g_hash_table_new(g_str_hash, g_str_equal);
2080  info.conf = conf;
2081 
2082  extract_global_info(node, &info);
2083
2084  if (info.key == NULL || info.type == GCONF_VALUE_INVALID)
2085    {
2086      g_free(info.owner);
2087
2088      if (info.global_default)
2089        gconf_value_free(info.global_default);
2090
2091      return 1;
2092    }
2093 
2094  iter = node->childs;
2095
2096  while (iter != NULL)
2097    {
2098      if (iter->type == XML_ELEMENT_NODE)
2099        {
2100          if (strcmp(iter->name, "key") == 0)
2101            ; /* nothing */
2102          else if (strcmp(iter->name, "owner") == 0)
2103            ;  /* nothing */
2104          else if (strcmp(iter->name, "type") == 0)
2105            ;  /* nothing */
2106          else if (strcmp(iter->name, "list_type") == 0)
2107            ;  /* nothing */
2108          else if (strcmp(iter->name, "car_type") == 0)
2109            ;  /* nothing */
2110          else if (strcmp(iter->name, "cdr_type") == 0)
2111            ;  /* nothing */
2112          else if (strcmp(iter->name, "default") == 0)
2113            ;  /* nothing */
2114          else if (strcmp(iter->name, "applyto") == 0)
2115            ;  /* nothing */
2116          else if (strcmp(iter->name, "locale") == 0)
2117            {
2118              process_locale_info(iter, &info);
2119            }
2120          else
2121            fprintf(stderr, _("WARNING: node <%s> not understood below <schema>\n"),
2122                    iter->name);
2123        }
2124         
2125      iter = iter->next;
2126    }
2127
2128  /* Attach schema to keys */
2129
2130  process_key_list(conf, info.key, info.apply_to);
2131
2132  if (g_hash_table_size(info.hash) == 0)
2133    {
2134      fprintf(stderr, _("You must have at least one <locale> entry in a <schema>\n"));
2135      return 1;
2136    }
2137     
2138  /* Now install each schema in the hash into the GConfEngine */
2139  g_hash_table_foreach(info.hash, hash_foreach, &info);
2140
2141  g_hash_table_destroy(info.hash);
2142
2143  g_free(info.key);
2144  g_free(info.owner);
2145  if (info.global_default)
2146    gconf_value_free(info.global_default);
2147 
2148  return 0;
2149}
2150
2151static int
2152process_schema_list(GConfEngine* conf, xmlNodePtr node)
2153{
2154  xmlNodePtr iter;
2155
2156  iter = node->childs;
2157
2158  while (iter != NULL)
2159    {
2160      if (iter->type == XML_ELEMENT_NODE)
2161        {
2162          if (strcmp(iter->name, "schema") == 0)
2163            process_schema(conf, iter);
2164          else
2165            fprintf(stderr, _("WARNING: node <%s> not understood below <schemalist>\n"),
2166                    iter->name);
2167        }
2168     
2169      iter = iter->next;
2170    }
2171
2172  return 0;
2173}
2174
2175static int
2176do_load_schema_file(GConfEngine* conf, const gchar* file)
2177{
2178  xmlDocPtr doc;
2179  xmlNodePtr iter;
2180  GError * err = NULL;
2181 
2182  errno = 0;
2183  doc = xmlParseFile(file);
2184
2185  if (doc == NULL)
2186    {
2187      if (errno != 0)
2188        fprintf(stderr, _("Failed to open `%s': %s\n"),
2189                file, strerror(errno));
2190      return 1;
2191    }
2192
2193  if (doc->root == NULL)
2194    {
2195      fprintf(stderr, _("Document `%s' is empty?\n"),
2196              file);
2197      return 1;
2198    }
2199
2200  iter = doc->root;
2201  while (iter != NULL)
2202    {
2203      if (iter->type == XML_ELEMENT_NODE)
2204        {
2205          if (strcmp(iter->name, "gconfschemafile") != 0)
2206            {
2207              fprintf(stderr, _("Document `%s' has the wrong type of root node (<%s>, should be <gconfschemafile>)\n"),
2208                      file, iter->name);
2209              return 1;
2210            }
2211          else
2212            break;
2213        }         
2214
2215      iter = iter->next;
2216    }
2217 
2218  if (iter == NULL)
2219    {
2220      fprintf(stderr, _("Document `%s' has no top level <gconfschemafile> node\n"),
2221              file);
2222      return 1;
2223    }
2224
2225  iter = iter->childs;
2226
2227  while (iter != NULL)
2228    {
2229      if (iter->type == XML_ELEMENT_NODE)
2230        {
2231          if (strcmp(iter->name, "schemalist") == 0)
2232            process_schema_list(conf, iter);
2233          else
2234            fprintf(stderr, _("WARNING: node <%s> below <gconfschemafile> not understood\n"),
2235                    iter->name);
2236        }
2237         
2238      iter = iter->next;
2239    }
2240
2241  gconf_engine_suggest_sync(conf, &err);
2242
2243  if (err != NULL)
2244    {
2245      fprintf(stderr, _("Error syncing config data: %s"),
2246              err->message);
2247      g_error_free(err);
2248      return 1;
2249    }
2250 
2251  return 0;
2252}
2253
2254static int
2255do_makefile_install(GConfEngine* conf, const gchar** args)
2256{
2257  GError* err = NULL;
2258 
2259  if (args == NULL)
2260    {
2261      fprintf(stderr, _("Must specify some schema files to install\n"));
2262      return 1;
2263    }
2264
2265  while (*args)
2266    {
2267      if (do_load_schema_file(conf, *args) != 0)
2268        return 1;
2269
2270      ++args;
2271    }
2272
2273  gconf_engine_suggest_sync(conf, &err);
2274
2275  if (err != NULL)
2276    {
2277      fprintf(stderr, _("Error syncing config data: %s"),
2278              err->message);
2279      g_error_free(err);
2280      return 1;
2281    }
2282 
2283  return 0;
2284}
2285
2286typedef enum {
2287  BreakageSetBadValues,
2288  BreakageCleanup
2289} BreakagePhase;
2290
2291static gboolean
2292check_err(GError** err)
2293{
2294  printf(".");
2295 
2296  if (*err != NULL)
2297    {
2298      fprintf(stderr, _("\n%s\n"),
2299              (*err)->message);
2300      g_error_free(*err);
2301      *err = NULL;
2302      return TRUE;
2303    }
2304  else
2305    return FALSE;
2306}
2307
2308static gboolean
2309key_breakage(GConfEngine* conf, const gchar* key, BreakagePhase phase)
2310{
2311  GError* error = NULL;
2312 
2313  if (phase == BreakageCleanup)
2314    {
2315      gconf_engine_unset(conf, key, &error);
2316      if (error != NULL)
2317        {
2318          fprintf(stderr, _("Failed to unset breakage key %s: %s\n"),
2319                  key, error->message);
2320          g_error_free(error);
2321          return FALSE;
2322        }
2323    }
2324  else if (phase == BreakageSetBadValues)
2325    {
2326      gint an_int = 43;
2327      gboolean a_bool = TRUE;
2328      gdouble a_float = 43695.435;
2329      const gchar* a_string = "Hello";
2330      GConfValue* val;
2331      GSList* list = NULL;
2332     
2333      printf("  +");
2334     
2335      gconf_engine_set_string(conf, key, "", &error);
2336      if (check_err(&error))
2337        return FALSE;
2338     
2339      gconf_engine_set_string(conf, key, "blah blah blah 93475028934670 @%^%$&%$&^%", &error);
2340      if (check_err(&error))
2341        return FALSE;
2342     
2343      gconf_engine_set_bool(conf, key, TRUE, &error);
2344      if (check_err(&error))
2345        return FALSE;
2346
2347      gconf_engine_set_bool(conf, key, FALSE, &error);
2348      if (check_err(&error))
2349        return FALSE;
2350
2351      gconf_engine_set_float(conf, key, 100.0, &error);
2352      if (check_err(&error))
2353        return FALSE;
2354
2355      gconf_engine_set_float(conf, key, -100.0, &error);
2356      if (check_err(&error))
2357        return FALSE;
2358
2359      gconf_engine_set_float(conf, key, 0.0, &error);
2360      if (check_err(&error))
2361        return FALSE;
2362
2363      gconf_engine_set_int(conf, key, 0, &error);
2364      if (check_err(&error))
2365        return FALSE;
2366
2367      gconf_engine_set_int(conf, key, 5384750, &error);
2368      if (check_err(&error))
2369        return FALSE;
2370     
2371      gconf_engine_set_int(conf, key, -11, &error);
2372      if (check_err(&error))
2373        return FALSE;
2374
2375      gconf_engine_set_list(conf, key, GCONF_VALUE_BOOL, list, &error);
2376      if (check_err(&error))
2377        return FALSE;
2378
2379      gconf_engine_set_pair(conf, key, GCONF_VALUE_INT, GCONF_VALUE_BOOL,
2380                            &an_int, &a_bool, &error);
2381      if (check_err(&error))
2382        return FALSE;
2383
2384      gconf_engine_set_pair(conf, key, GCONF_VALUE_FLOAT, GCONF_VALUE_STRING,
2385                            &a_float, &a_string, &error);
2386      if (check_err(&error))
2387        return FALSE;
2388
2389      /* empty pair */
2390      val = gconf_value_new(GCONF_VALUE_PAIR);
2391      gconf_engine_set (conf, key, val, &error);
2392      gconf_value_free(val);
2393      if (check_err(&error))
2394        return FALSE;
2395
2396      list = NULL;
2397      gconf_engine_set_list(conf, key, GCONF_VALUE_STRING, list, &error);
2398      if (check_err(&error))
2399        return FALSE;
2400      gconf_engine_set_list(conf, key, GCONF_VALUE_INT, list, &error);
2401      if (check_err(&error))
2402        return FALSE;
2403      gconf_engine_set_list(conf, key, GCONF_VALUE_BOOL, list, &error);
2404      if (check_err(&error))
2405        return FALSE;
2406
2407      list = g_slist_prepend(list, GINT_TO_POINTER(10));
2408      list = g_slist_prepend(list, GINT_TO_POINTER(14));
2409      list = g_slist_prepend(list, GINT_TO_POINTER(-93));
2410      list = g_slist_prepend(list, GINT_TO_POINTER(1000000));
2411      list = g_slist_prepend(list, GINT_TO_POINTER(32));
2412      gconf_engine_set_list(conf, key, GCONF_VALUE_INT, list, &error);
2413      if (check_err(&error))
2414        return FALSE;
2415
2416      g_slist_free(list);
2417      list = NULL;
2418
2419      list = g_slist_prepend(list, "");
2420      list = g_slist_prepend(list, "blah");
2421      list = g_slist_prepend(list, "");
2422      list = g_slist_prepend(list, "\n\t\r\n     \n");
2423      list = g_slist_prepend(list, "woo fooo s^%*^%&@^$@%&@%$");
2424      gconf_engine_set_list(conf, key, GCONF_VALUE_STRING, list, &error);
2425      if (check_err(&error))
2426        return FALSE;
2427
2428      g_slist_free(list);
2429      list = NULL;
2430     
2431      printf("\n");
2432    }
2433  else
2434    g_assert_not_reached();
2435     
2436  return TRUE;
2437}
2438
2439static int
2440do_break_key(GConfEngine* conf, const gchar** args)
2441{
2442  if (args == NULL)
2443    {
2444      fprintf(stderr, _("Must specify some keys to break\n"));
2445      return 1;
2446    }
2447 
2448  while (*args)
2449    {
2450      printf(_("Trying to break your application by setting bad values for key:\n  %s\n"), *args);
2451     
2452      if (!key_breakage(conf, *args, BreakageSetBadValues))
2453        return 1;
2454      if (!key_breakage(conf, *args, BreakageCleanup))
2455        return 1;
2456
2457      ++args;
2458    }
2459
2460  return 0;
2461}
2462
2463static int
2464do_break_directory(GConfEngine* conf, const gchar** args)
2465{
2466  if (args == NULL)
2467    {
2468      fprintf(stderr, _("Must specify some directories to break\n"));
2469      return 1;
2470    }
2471 
2472  while (*args)
2473    {
2474      gchar* keys[10] = { NULL };
2475      gchar* full_keys[10] = { NULL };
2476      int i;
2477
2478      i = 0;
2479      while (i < 10)
2480        {
2481          keys[i] = gconf_unique_key();
2482          full_keys[i] = gconf_concat_dir_and_key(*args, keys[i]);
2483
2484          ++i;
2485        }
2486
2487      printf(_("Trying to break your application by setting bad values for keys in directory:\n  %s\n"), *args);
2488
2489      i = 0;
2490      while (i < 10)
2491        {
2492          if (!key_breakage(conf, full_keys[i], BreakageSetBadValues))
2493            return 1;
2494
2495          ++i;
2496        }
2497     
2498      i = 0;
2499      while (i < 10)
2500        {
2501          if (!key_breakage(conf, full_keys[i], BreakageCleanup))
2502            return 1;
2503         
2504          ++i;
2505        }
2506
2507      i = 0;
2508      while (i < 10)
2509        {
2510          g_free(keys[i]);
2511          g_free(full_keys[i]);
2512
2513          ++i;
2514        }
2515     
2516      ++args;
2517    }
2518
2519  return 0;
2520}
2521
2522static int
2523do_get_default_source(GConfEngine* conf, const gchar** args)
2524{
2525  gchar *source;
2526  gchar buf[512];
2527  FILE *f;
2528
2529  /* Try with $sysconfdir/gconf/schema-install-source */
2530  f = fopen(GCONF_ETCDIR"/schema-install-source", "r");
2531
2532  if (f != NULL)
2533    {
2534      source = fgets(buf, 512, f);
2535      fclose(f); 
2536      if (source)
2537        {
2538          g_strchomp(source);
2539          if (*source != '\0')
2540            {
2541              printf("%s\n", source);
2542              return 0;
2543            }
2544        }
2545    }
2546
2547  /* Use default database */
2548  source = g_strconcat("xml::", GCONF_ETCDIR, "/gconf.xml.defaults", NULL);
2549  printf("%s\n", source);
2550  g_free(source);
2551
2552  return 0;
2553}
Note: See TracBrowser for help on using the repository browser.