aboutsummaryrefslogtreecommitdiff
path: root/src/mint/taler-mint-httpd_parsing.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/mint/taler-mint-httpd_parsing.c')
-rw-r--r--src/mint/taler-mint-httpd_parsing.c156
1 files changed, 87 insertions, 69 deletions
diff --git a/src/mint/taler-mint-httpd_parsing.c b/src/mint/taler-mint-httpd_parsing.c
index 19c88d456..7d3f3b5e6 100644
--- a/src/mint/taler-mint-httpd_parsing.c
+++ b/src/mint/taler-mint-httpd_parsing.c
@@ -271,44 +271,48 @@ TALER_MINT_parse_post_cleanup_callback (void *con_cls)
271 * @param ... navigation specification (see JNAV_*) 271 * @param ... navigation specification (see JNAV_*)
272 * @return GNUNET_YES if navigation was successful 272 * @return GNUNET_YES if navigation was successful
273 * GNUNET_NO if json is malformed, error response was generated 273 * GNUNET_NO if json is malformed, error response was generated
274 * GNUNET_SYSERR on internal error 274 * GNUNET_SYSERR on internal error (no response was generated,
275 * connection must be closed)
275 */ 276 */
276int 277int
277request_json_require_nav (struct MHD_Connection *connection, 278GNUNET_MINT_parse_navigate_json (struct MHD_Connection *connection,
278 const json_t *root, ...) 279 const json_t *root,
280 ...)
279{ 281{
280 va_list argp; 282 va_list argp;
281 int ignore = GNUNET_NO; 283 int ret;
282 // what's our current path from 'root'? 284 json_t *path; /* what's our current path from 'root'? */
283 json_t *path;
284 285
285 path = json_array (); 286 path = json_array ();
286 287 va_start (argp, root);
287 va_start(argp, root); 288 ret = 2;
288 289 while (2 == ret)
289 while (1)
290 { 290 {
291 int command = va_arg(argp, int); 291 enum TALER_MINT_JsonNavigationCommand command
292 = va_arg (argp,
293 enum TALER_MINT_JsonNavigationCommand);
294
292 switch (command) 295 switch (command)
293 { 296 {
294 case JNAV_FIELD: 297 case JNAV_FIELD:
295 { 298 {
296 const char *fname = va_arg(argp, const char *); 299 const char *fname = va_arg(argp, const char *);
297 if (GNUNET_YES == ignore) 300
298 break; 301 json_array_append_new (path,
299 json_array_append_new (path, json_string (fname)); 302 json_string (fname));
300 root = json_object_get (root, fname); 303 root = json_object_get (root,
304 fname);
301 if (NULL == root) 305 if (NULL == root)
302 { 306 {
303 /* FIXME: can't IGNORE this return value! */ 307 ret = (MHD_YES ==
304 (void) TALER_MINT_reply_json_pack (connection, 308 TALER_MINT_reply_json_pack (connection,
305 MHD_HTTP_BAD_REQUEST, 309 MHD_HTTP_BAD_REQUEST,
306 "{s:s,s:o}", 310 "{s:s,s:o}",
307 "error", 311 "error",
308 "missing field in JSON", 312 "missing field in JSON",
309 "path", 313 "path",
310 path); 314 path))
311 ignore = GNUNET_YES; 315 ? GNUNET_NO : GNUNET_SYSERR;
312 break; 316 break;
313 } 317 }
314 } 318 }
@@ -316,19 +320,21 @@ request_json_require_nav (struct MHD_Connection *connection,
316 case JNAV_INDEX: 320 case JNAV_INDEX:
317 { 321 {
318 int fnum = va_arg(argp, int); 322 int fnum = va_arg(argp, int);
319 if (GNUNET_YES == ignore) 323
320 break; 324 json_array_append_new (path,
321 json_array_append_new (path, json_integer (fnum)); 325 json_integer (fnum));
322 root = json_array_get (root, fnum); 326 root = json_array_get (root,
327 fnum);
323 if (NULL == root) 328 if (NULL == root)
324 { 329 {
325 /* FIXME: can't IGNORE this return value! */ 330 ret = (MHD_YES ==
326 (void) TALER_MINT_reply_json_pack (connection, 331 TALER_MINT_reply_json_pack (connection,
327 MHD_HTTP_BAD_REQUEST, 332 MHD_HTTP_BAD_REQUEST,
328 "{s:s, s:o}", 333 "{s:s, s:o}",
329 "error", "missing index in JSON", 334 "error",
330 "path", path); 335 "missing index in JSON",
331 ignore = GNUNET_YES; 336 "path", path))
337 ? GNUNET_NO : GNUNET_SYSERR;
332 break; 338 break;
333 } 339 }
334 } 340 }
@@ -340,36 +346,36 @@ request_json_require_nav (struct MHD_Connection *connection,
340 const char *str; 346 const char *str;
341 int res; 347 int res;
342 348
343 va_end(argp);
344 if (GNUNET_YES == ignore)
345 return GNUNET_NO;
346 str = json_string_value (root); 349 str = json_string_value (root);
347 if (NULL == str) 350 if (NULL == str)
348 { 351 {
349 /* FIXME: can't IGNORE this return value! */ 352 ret = (MHD_YES ==
350 (void) TALER_MINT_reply_json_pack (connection, 353 TALER_MINT_reply_json_pack (connection,
351 MHD_HTTP_BAD_REQUEST, 354 MHD_HTTP_BAD_REQUEST,
352 "{s:s, s:o}", 355 "{s:s, s:o}",
353 "error", 356 "error",
354 "string expected", 357 "string expected",
355 "path", 358 "path",
356 path); 359 path))
357 return GNUNET_NO; 360 ? GNUNET_NO : GNUNET_SYSERR;
361 break;
358 } 362 }
359 res = GNUNET_STRINGS_string_to_data (str, strlen (str), 363 res = GNUNET_STRINGS_string_to_data (str, strlen (str),
360 where, len); 364 where, len);
361 if (GNUNET_OK != res) 365 if (GNUNET_OK != res)
362 { 366 {
363 /* FIXME: can't IGNORE this return value! */ 367 ret = (MHD_YES ==
364 (void) TALER_MINT_reply_json_pack (connection, 368 TALER_MINT_reply_json_pack (connection,
365 MHD_HTTP_BAD_REQUEST, 369 MHD_HTTP_BAD_REQUEST,
366 "{s:s,s:o}", 370 "{s:s,s:o}",
367 "error", 371 "error",
368 "malformed binary data in JSON", 372 "malformed binary data in JSON",
369 "path", path); 373 "path",
370 return GNUNET_NO; 374 path))
375 ? GNUNET_NO : GNUNET_SYSERR;
376 break;
371 } 377 }
372 return GNUNET_YES; 378 ret = GNUNET_OK;
373 } 379 }
374 break; 380 break;
375 case JNAV_RET_DATA_VAR: 381 case JNAV_RET_DATA_VAR:
@@ -378,35 +384,42 @@ request_json_require_nav (struct MHD_Connection *connection,
378 size_t *len = va_arg (argp, size_t *); 384 size_t *len = va_arg (argp, size_t *);
379 const char *str; 385 const char *str;
380 386
381 va_end(argp);
382 if (GNUNET_YES == ignore)
383 return GNUNET_NO;
384 str = json_string_value (root); 387 str = json_string_value (root);
385 if (NULL == str) 388 if (NULL == str)
386 { 389 {
387 GNUNET_break (0); 390 ret = (MHD_YES ==
388 return GNUNET_SYSERR; 391 TALER_MINT_reply_internal_error (connection,
392 "json_string_value() failed"))
393 ? GNUNET_NO : GNUNET_SYSERR;
394 break;
389 } 395 }
390 *len = (strlen (str) * 5) / 8; 396 *len = (strlen (str) * 5) / 8;
391 if (where != NULL) 397 if (NULL != where)
392 { 398 {
393 int res; 399 int res;
400
394 *where = GNUNET_malloc (*len); 401 *where = GNUNET_malloc (*len);
395 res = GNUNET_STRINGS_string_to_data (str, strlen (str), 402 res = GNUNET_STRINGS_string_to_data (str,
396 *where, *len); 403 strlen (str),
404 *where,
405 *len);
397 if (GNUNET_OK != res) 406 if (GNUNET_OK != res)
398 { 407 {
399 /* FIXME: can't IGNORE this return value! */ 408 GNUNET_free (*where);
400 (void) TALER_MINT_reply_json_pack (connection, 409 *where = NULL;
410 *len = 0;
411 ret = (MHD_YES ==
412 TALER_MINT_reply_json_pack (connection,
401 MHD_HTTP_BAD_REQUEST, 413 MHD_HTTP_BAD_REQUEST,
402 "{s:s, s:o}", 414 "{s:s, s:o}",
403 "error", 415 "error",
404 "malformed binary data in JSON", 416 "malformed binary data in JSON",
405 "path", path); 417 "path", path))
406 return GNUNET_NO; 418 ? GNUNET_NO : GNUNET_SYSERR;
419 break;
407 } 420 }
408 } 421 }
409 return GNUNET_OK; 422 ret = GNUNET_OK;
410 } 423 }
411 break; 424 break;
412 case JNAV_RET_TYPED_JSON: 425 case JNAV_RET_TYPED_JSON:
@@ -414,30 +427,35 @@ request_json_require_nav (struct MHD_Connection *connection,
414 int typ = va_arg (argp, int); 427 int typ = va_arg (argp, int);
415 const json_t **r_json = va_arg (argp, const json_t **); 428 const json_t **r_json = va_arg (argp, const json_t **);
416 429
417 va_end(argp); 430 if ( (-1 != typ) && (json_typeof (root) != typ))
418 if (GNUNET_YES == ignore)
419 return GNUNET_NO;
420 if (typ != -1 && json_typeof (root) != typ)
421 { 431 {
422 /* FIXME: can't IGNORE this return value! */ 432 ret = (MHD_YES ==
423 (void) TALER_MINT_reply_json_pack (connection, 433 TALER_MINT_reply_json_pack (connection,
424 MHD_HTTP_BAD_REQUEST, 434 MHD_HTTP_BAD_REQUEST,
425 "{s:s, s:i, s:i s:o}", 435 "{s:s, s:i, s:i s:o}",
426 "error", "wrong JSON field type", 436 "error", "wrong JSON field type",
427 "type_expected", typ, 437 "type_expected", typ,
428 "type_actual", json_typeof (root), 438 "type_actual", json_typeof (root),
429 "path", path); 439 "path", path))
430 return GNUNET_NO; 440 ? GNUNET_NO : GNUNET_SYSERR;
441 break;
431 } 442 }
432 *r_json = root; 443 *r_json = root;
433 return GNUNET_OK; 444 ret = GNUNET_OK;
434 } 445 }
435 break; 446 break;
436 default: 447 default:
437 GNUNET_assert (0); 448 GNUNET_break (0);
449 ret = (MHD_YES ==
450 TALER_MINT_reply_internal_error (connection,
451 "unhandled value in switch"))
452 ? GNUNET_NO : GNUNET_SYSERR;
453 break;
438 } 454 }
439 } 455 }
440 GNUNET_assert (0); 456 va_end (argp);
457 json_decref (path);
458 return ret;
441} 459}
442 460
443 461