12bc5c1ea8e32dada775094073ff7b7d2050864d
[oweals/gnunet.git] / src / fs / fs_getopt.c
1 /*
2      This file is part of GNUnet.
3      Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009 Christian Grothoff (and other contributing authors)
4
5      GNUnet is free software; you can redistribute it and/or modify
6      it under the terms of the GNU General Public License as published
7      by the Free Software Foundation; either version 3, or (at your
8      option) any later version.
9
10      GNUnet is distributed in the hope that it will be useful, but
11      WITHOUT ANY WARRANTY; without even the implied warranty of
12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13      General Public License for more details.
14
15      You should have received a copy of the GNU General Public License
16      along with GNUnet; see the file COPYING.  If not, write to the
17      Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18      Boston, MA 02110-1301, USA.
19 */
20
21 /**
22  * @file fs/fs_getopt.c
23  * @brief helper functions for command-line argument processing
24  * @author Igor Wronsky, Christian Grothoff
25  */
26 #include "platform.h"
27 #include "gnunet_fs_service.h"
28 #include "fs_api.h"
29
30 /* ******************** command-line option parsing API ******************** */
31
32 /**
33  * Command-line option parser function that allows the user
34  * to specify one or more '-k' options with keywords.  Each
35  * specified keyword will be added to the URI.  A pointer to
36  * the URI must be passed as the "scls" argument.
37  *
38  * @param ctx command line processor context
39  * @param scls must be of type "struct GNUNET_FS_Uri **"
40  * @param option name of the option (typically 'k')
41  * @param value command line argument given
42  * @return GNUNET_OK on success
43  */
44 int
45 GNUNET_FS_getopt_set_keywords (struct GNUNET_GETOPT_CommandLineProcessorContext
46                                *ctx, void *scls, const char *option,
47                                const char *value)
48 {
49   struct GNUNET_FS_Uri **uri = scls;
50   struct GNUNET_FS_Uri *u = *uri;
51   char *val;
52   size_t slen;
53
54   if (u == NULL)
55   {
56     u = GNUNET_new (struct GNUNET_FS_Uri);
57     *uri = u;
58     u->type = GNUNET_FS_URI_KSK;
59     u->data.ksk.keywordCount = 0;
60     u->data.ksk.keywords = NULL;
61   }
62   else
63   {
64     GNUNET_assert (u->type == GNUNET_FS_URI_KSK);
65   }
66   slen = strlen (value);
67   if (slen == 0)
68     return GNUNET_SYSERR;       /* cannot be empty */
69   if (value[0] == '+')
70   {
71     /* simply preserve the "mandatory" flag */
72     if (slen < 2)
73       return GNUNET_SYSERR;     /* empty keywords not allowed */
74     if ((value[1] == '"') && (slen > 3) && (value[slen - 1] == '"'))
75     {
76       /* remove the quotes, keep the '+' */
77       val = GNUNET_malloc (slen - 1);
78       val[0] = '+';
79       memcpy (&val[1], &value[2], slen - 3);
80       val[slen - 2] = '\0';
81     }
82     else
83     {
84       /* no quotes, just keep the '+' */
85       val = GNUNET_strdup (value);
86     }
87   }
88   else
89   {
90     if ((value[0] == '"') && (slen > 2) && (value[slen - 1] == '"'))
91     {
92       /* remove the quotes, add a space */
93       val = GNUNET_malloc (slen);
94       val[0] = ' ';
95       memcpy (&val[1], &value[1], slen - 2);
96       val[slen - 1] = '\0';
97     }
98     else
99     {
100       /* add a space to indicate "not mandatory" */
101       val = GNUNET_malloc (slen + 2);
102       strcpy (val, " ");
103       strcat (val, value);
104     }
105   }
106   GNUNET_array_append (u->data.ksk.keywords, u->data.ksk.keywordCount, val);
107   return GNUNET_OK;
108 }
109
110
111 /**
112  * Command-line option parser function that allows the user to specify
113  * one or more '-m' options with metadata.  Each specified entry of
114  * the form "type=value" will be added to the metadata.  A pointer to
115  * the metadata must be passed as the "scls" argument.
116  *
117  * @param ctx command line processor context
118  * @param scls must be of type "struct GNUNET_MetaData **"
119  * @param option name of the option (typically 'k')
120  * @param value command line argument given
121  * @return #GNUNET_OK on success
122  */
123 int
124 GNUNET_FS_getopt_set_metadata (struct GNUNET_GETOPT_CommandLineProcessorContext *ctx,
125                                void *scls,
126                                const char *option,
127                                const char *value)
128 {
129   struct GNUNET_CONTAINER_MetaData **mm = scls;
130 #if HAVE_EXTRACTOR_H
131   enum EXTRACTOR_MetaType type;
132   const char *typename;
133   const char *typename_i18n;
134 #endif
135   struct GNUNET_CONTAINER_MetaData *meta;
136   char *tmp;
137
138   meta = *mm;
139   if (meta == NULL)
140   {
141     meta = GNUNET_CONTAINER_meta_data_create ();
142     *mm = meta;
143   }
144
145   /* Use GNUNET_STRINGS_get_utf8_args() in main() to acquire utf-8-encoded
146    * commandline arguments, so that the following line is not needed.
147    */
148   /*tmp = GNUNET_STRINGS_to_utf8 (value, strlen (value), locale_charset ());*/
149   tmp = GNUNET_strdup (value);
150 #if HAVE_EXTRACTOR_H
151   type = EXTRACTOR_metatype_get_max ();
152   while (type > 0)
153   {
154     type--;
155     typename = EXTRACTOR_metatype_to_string (type);
156     typename_i18n = dgettext (LIBEXTRACTOR_GETTEXT_DOMAIN, typename);
157     if ((strlen (tmp) >= strlen (typename) + 1) &&
158         (tmp[strlen (typename)] == ':') &&
159         (0 == strncmp (typename, tmp, strlen (typename))))
160     {
161       GNUNET_CONTAINER_meta_data_insert (meta, "<gnunet>", type,
162                                          EXTRACTOR_METAFORMAT_UTF8,
163                                          "text/plain",
164                                          &tmp[strlen (typename) + 1],
165                                          strlen (&tmp[strlen (typename) + 1]) +
166                                          1);
167       GNUNET_free (tmp);
168       tmp = NULL;
169       break;
170     }
171     if ((strlen (tmp) >= strlen (typename_i18n) + 1) &&
172         (tmp[strlen (typename_i18n)] == ':') &&
173         (0 == strncmp (typename_i18n, tmp, strlen (typename_i18n))))
174     {
175       GNUNET_CONTAINER_meta_data_insert (meta, "<gnunet>", type,
176                                          EXTRACTOR_METAFORMAT_UTF8,
177                                          "text/plain",
178                                          &tmp[strlen (typename_i18n) + 1],
179                                          strlen (&tmp
180                                                  [strlen (typename_i18n) + 1]) +
181                                          1);
182       GNUNET_free (tmp);
183       tmp = NULL;
184       break;
185     }
186   }
187 #endif
188
189   if (NULL != tmp)
190   {
191     GNUNET_CONTAINER_meta_data_insert (meta, "<gnunet>",
192                                        EXTRACTOR_METATYPE_UNKNOWN,
193                                        EXTRACTOR_METAFORMAT_UTF8, "text/plain",
194                                        tmp, strlen (tmp) + 1);
195     GNUNET_free (tmp);
196     printf (_
197             ("Unknown metadata type in metadata option `%s'.  Using metadata type `unknown' instead.\n"),
198             value);
199   }
200   return GNUNET_OK;
201 }
202
203 /* end of fs_getopt.c */