]>
git.cameronkatri.com Git - mandoc.git/blob - argv.c
1 /* $Id: argv.c,v 1.7 2009/01/05 16:11:14 kristaps Exp $ */
3 * Copyright (c) 2008 Kristaps Dzonsons <kristaps@kth.se>
5 * Permission to use, copy, modify, and distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the
7 * above copyright notice and this permission notice appear in all
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
11 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
12 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
13 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
14 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
15 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
16 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17 * PERFORMANCE OF THIS SOFTWARE.
29 static int lookup(int, const char *);
30 static int parse(struct mdoc
*, int,
31 struct mdoc_arg
*, int *, char *);
32 static int postparse(struct mdoc
*, int,
33 const struct mdoc_arg
*, int);
37 mdoc_args(struct mdoc
*mdoc
, int tok
, int *pos
, char *buf
, int fl
, char **v
)
44 if ('\"' == buf
[*pos
] && ! (fl
& ARGS_QUOTED
))
45 if ( ! mdoc_warn(mdoc
, tok
, *pos
, WARN_SYNTAX_QUOTED
))
49 if ( ! mdoc_warn(mdoc
, tok
, *pos
, WARN_SYNTAX_ARGLIKE
))
52 if ((fl
& ARGS_DELIM
) && mdoc_iscdelim(buf
[*pos
])) {
53 for (i
= *pos
; buf
[i
]; ) {
54 if ( ! mdoc_iscdelim(buf
[i
]))
57 if (0 == buf
[i
] || ! isspace(buf
[i
]))
60 while (buf
[i
] && isspace(buf
[i
]))
70 * Parse routine for non-quoted string.
73 if ('\"' != buf
[*pos
]) {
76 while (buf
[*pos
] && ! isspace(buf
[*pos
]))
86 while (buf
[*pos
] && isspace(buf
[*pos
]))
92 if ( ! mdoc_warn(mdoc
, tok
, *pos
, WARN_SYNTAX_WS_EOLN
))
99 * If we're a quoted string (and quoted strings are allowed),
100 * then parse ahead to the next quote. If none's found, it's an
101 * error. After, parse to the next word.
106 while (buf
[*pos
] && '\"' != buf
[*pos
])
109 if (0 == buf
[*pos
]) {
110 (void)mdoc_err(mdoc
, tok
, *pos
, ERR_SYNTAX_UNQUOTE
);
118 while (buf
[*pos
] && isspace(buf
[*pos
]))
124 if ( ! mdoc_warn(mdoc
, tok
, *pos
, WARN_SYNTAX_WS_EOLN
))
132 lookup(int tok
, const char *argv
)
137 if (xstrcmp(argv
, "emphasis"))
138 return(MDOC_Emphasis
);
139 else if (xstrcmp(argv
, "literal"))
140 return(MDOC_Literal
);
141 else if (xstrcmp(argv
, "symbolic"))
142 return(MDOC_Symbolic
);
146 if (xstrcmp(argv
, "split"))
148 else if (xstrcmp(argv
, "nosplit"))
149 return(MDOC_Nosplit
);
153 if (xstrcmp(argv
, "ragged"))
155 else if (xstrcmp(argv
, "unfilled"))
156 return(MDOC_Unfilled
);
157 else if (xstrcmp(argv
, "literal"))
158 return(MDOC_Literal
);
159 else if (xstrcmp(argv
, "file"))
161 else if (xstrcmp(argv
, "offset"))
166 if (xstrcmp(argv
, "words"))
171 if (xstrcmp(argv
, "bullet"))
173 else if (xstrcmp(argv
, "dash"))
175 else if (xstrcmp(argv
, "hyphen"))
177 else if (xstrcmp(argv
, "item"))
179 else if (xstrcmp(argv
, "enum"))
181 else if (xstrcmp(argv
, "tag"))
183 else if (xstrcmp(argv
, "diag"))
185 else if (xstrcmp(argv
, "hang"))
187 else if (xstrcmp(argv
, "ohang"))
189 else if (xstrcmp(argv
, "inset"))
191 else if (xstrcmp(argv
, "column"))
193 else if (xstrcmp(argv
, "width"))
195 else if (xstrcmp(argv
, "offset"))
197 else if (xstrcmp(argv
, "compact"))
198 return(MDOC_Compact
);
204 if (xstrcmp(argv
, "std"))
209 if (xstrcmp(argv
, "p1003.1-88"))
210 return(MDOC_p1003_1_88
);
211 else if (xstrcmp(argv
, "p1003.1-90"))
212 return(MDOC_p1003_1_90
);
213 else if (xstrcmp(argv
, "p1003.1-96"))
214 return(MDOC_p1003_1_96
);
215 else if (xstrcmp(argv
, "p1003.1-2001"))
216 return(MDOC_p1003_1_2001
);
217 else if (xstrcmp(argv
, "p1003.1-2004"))
218 return(MDOC_p1003_1_2004
);
219 else if (xstrcmp(argv
, "p1003.1"))
220 return(MDOC_p1003_1
);
221 else if (xstrcmp(argv
, "p1003.1b"))
222 return(MDOC_p1003_1b
);
223 else if (xstrcmp(argv
, "p1003.1b-93"))
224 return(MDOC_p1003_1b_93
);
225 else if (xstrcmp(argv
, "p1003.1c-95"))
226 return(MDOC_p1003_1c_95
);
227 else if (xstrcmp(argv
, "p1003.1g-2000"))
228 return(MDOC_p1003_1g_2000
);
229 else if (xstrcmp(argv
, "p1003.2-92"))
230 return(MDOC_p1003_2_92
);
231 else if (xstrcmp(argv
, "p1003.2-95"))
232 return(MDOC_p1387_2_95
);
233 else if (xstrcmp(argv
, "p1003.2"))
234 return(MDOC_p1003_2
);
235 else if (xstrcmp(argv
, "p1387.2-95"))
236 return(MDOC_p1387_2
);
237 else if (xstrcmp(argv
, "isoC-90"))
238 return(MDOC_isoC_90
);
239 else if (xstrcmp(argv
, "isoC-amd1"))
240 return(MDOC_isoC_amd1
);
241 else if (xstrcmp(argv
, "isoC-tcor1"))
242 return(MDOC_isoC_tcor1
);
243 else if (xstrcmp(argv
, "isoC-tcor2"))
244 return(MDOC_isoC_tcor2
);
245 else if (xstrcmp(argv
, "isoC-99"))
246 return(MDOC_isoC_99
);
247 else if (xstrcmp(argv
, "ansiC"))
249 else if (xstrcmp(argv
, "ansiC-89"))
250 return(MDOC_ansiC_89
);
251 else if (xstrcmp(argv
, "ansiC-99"))
252 return(MDOC_ansiC_99
);
253 else if (xstrcmp(argv
, "ieee754"))
254 return(MDOC_ieee754
);
255 else if (xstrcmp(argv
, "iso8802-3"))
256 return(MDOC_iso8802_3
);
257 else if (xstrcmp(argv
, "xpg3"))
259 else if (xstrcmp(argv
, "xpg4"))
261 else if (xstrcmp(argv
, "xpg4.2"))
263 else if (xstrcmp(argv
, "xpg4.3"))
265 else if (xstrcmp(argv
, "xbd5"))
267 else if (xstrcmp(argv
, "xcu5"))
269 else if (xstrcmp(argv
, "xsh5"))
271 else if (xstrcmp(argv
, "xns5"))
273 else if (xstrcmp(argv
, "xns5.2d2.0"))
274 return(MDOC_xns5_2d2_0
);
275 else if (xstrcmp(argv
, "xcurses4.2"))
276 return(MDOC_xcurses4_2
);
277 else if (xstrcmp(argv
, "susv2"))
279 else if (xstrcmp(argv
, "susv3"))
281 else if (xstrcmp(argv
, "svid4"))
290 return(MDOC_ARG_MAX
);
295 postparse(struct mdoc
*mdoc
, int tok
, const struct mdoc_arg
*v
, int pos
)
302 if (xstrcmp(v
->value
[0], "left"))
304 if (xstrcmp(v
->value
[0], "right"))
306 if (xstrcmp(v
->value
[0], "center"))
308 if (xstrcmp(v
->value
[0], "indent"))
310 if (xstrcmp(v
->value
[0], "indent-two"))
312 return(mdoc_err(mdoc
, tok
, pos
, ERR_SYNTAX_ARGBAD
));
322 parse(struct mdoc
*mdoc
, int tok
,
323 struct mdoc_arg
*v
, int *pos
, char *buf
)
337 * This has a single value for an argument.
339 c
= mdoc_args(mdoc
, tok
, pos
, buf
, ARGS_QUOTED
, &p
);
342 else if (ARGS_EOLN
== c
)
343 return(mdoc_err(mdoc
, tok
, ppos
, ERR_SYNTAX_ARGVAL
));
346 v
->value
= xcalloc(1, sizeof(char *));
352 * This has several value for a single argument. We
353 * pre-allocate a pointer array and don't let it exceed
357 v
->value
= xcalloc(MDOC_LINEARG_MAX
, sizeof(char *));
358 for (i
= 0; i
< MDOC_LINEARG_MAX
; i
++) {
359 c
= mdoc_args(mdoc
, tok
, pos
, buf
, ARGS_QUOTED
, &p
);
360 if (ARGS_ERROR
== c
) {
363 } else if (ARGS_EOLN
== c
)
369 return(mdoc_err(mdoc
, tok
, ppos
, ERR_SYNTAX_ARGVAL
));
370 } else if (MDOC_LINEARG_MAX
== i
)
371 return(mdoc_err(mdoc
, tok
, ppos
, ERR_SYNTAX_ARGMANY
));
387 mdoc_argv(struct mdoc
*mdoc
, int tok
,
388 struct mdoc_arg
*v
, int *pos
, char *buf
)
393 (void)memset(v
, 0, sizeof(struct mdoc_arg
));
398 assert( ! isspace(buf
[*pos
]));
400 if ('-' != buf
[*pos
])
404 argv
= &buf
[++(*pos
)];
406 while (buf
[*pos
] && ! isspace(buf
[*pos
]))
412 if (MDOC_ARG_MAX
== (v
->arg
= lookup(tok
, argv
))) {
413 (void)mdoc_err(mdoc
, tok
, i
, ERR_SYNTAX_ARG
);
417 while (buf
[*pos
] && isspace(buf
[*pos
]))
420 /* FIXME: whitespace if no value. */
423 if ( ! parse(mdoc
, tok
, v
, pos
, buf
))
425 if ( ! postparse(mdoc
, tok
, v
, ppos
))
433 mdoc_argv_free(int sz
, struct mdoc_arg
*arg
)
437 for (i
= 0; i
< sz
; i
++) {
438 if (0 == arg
[i
].sz
) {
439 assert(NULL
== arg
[i
].value
);
442 assert(arg
[i
].value
);