選択できるのは25トピックまでです。 トピックは、先頭が英数字で、英数字とダッシュ('-')を使用した35文字以内のものにしてください。

1038 行
29 KiB

  1. // This file is part of Jiffy released under the MIT license.
  2. // See the LICENSE file for more information.
  3. #include <assert.h>
  4. #include <errno.h>
  5. #include <stdio.h>
  6. #include <stdlib.h>
  7. #include <string.h>
  8. #include "erl_nif.h"
  9. #include "jiffy.h"
  10. #define U(c) ((unsigned char) (c))
  11. #define ERROR(i, msg) make_error(st, env, msg)
  12. #define STACK_SIZE_INC 64
  13. #define NUM_BUF_LEN 32
  14. #if WINDOWS || WIN32
  15. #define snprintf _snprintf
  16. #endif
  17. enum {
  18. st_value=0,
  19. st_object,
  20. st_array,
  21. st_key,
  22. st_colon,
  23. st_comma,
  24. st_done,
  25. st_invalid
  26. } JsonState;
  27. enum {
  28. nst_init=0,
  29. nst_sign,
  30. nst_mantissa,
  31. nst_frac0,
  32. nst_frac1,
  33. nst_frac,
  34. nst_esign,
  35. nst_edigit
  36. } JsonNumState;
  37. typedef struct {
  38. ErlNifEnv* env;
  39. jiffy_st* atoms;
  40. ERL_NIF_TERM arg;
  41. ErlNifBinary bin;
  42. size_t bytes_per_red;
  43. int is_partial;
  44. int return_maps;
  45. int return_trailer;
  46. int dedupe_keys;
  47. ERL_NIF_TERM null_term;
  48. char* p;
  49. unsigned char* u;
  50. int i;
  51. int len;
  52. char* st_data;
  53. int st_size;
  54. int st_top;
  55. } Decoder;
  56. Decoder*
  57. dec_new(ErlNifEnv* env)
  58. {
  59. jiffy_st* st = (jiffy_st*) enif_priv_data(env);
  60. Decoder* d = enif_alloc_resource(st->res_dec, sizeof(Decoder));
  61. int i;
  62. if(d == NULL) {
  63. return NULL;
  64. }
  65. d->atoms = st;
  66. d->bytes_per_red = DEFAULT_BYTES_PER_REDUCTION;
  67. d->is_partial = 0;
  68. d->return_maps = 0;
  69. d->return_trailer = 0;
  70. d->dedupe_keys = 0;
  71. d->null_term = d->atoms->atom_null;
  72. d->p = NULL;
  73. d->u = NULL;
  74. d->len = -1;
  75. d->i = -1;
  76. d->st_data = (char*) enif_alloc(STACK_SIZE_INC * sizeof(char));
  77. d->st_size = STACK_SIZE_INC;
  78. d->st_top = 0;
  79. for(i = 0; i < d->st_size; i++) {
  80. d->st_data[i] = st_invalid;
  81. }
  82. d->st_data[0] = st_value;
  83. d->st_top++;
  84. return d;
  85. }
  86. void
  87. dec_init(Decoder* d, ErlNifEnv* env, ERL_NIF_TERM arg, ErlNifBinary* bin)
  88. {
  89. d->env = env;
  90. d->arg = arg;
  91. d->p = (char*) bin->data;
  92. d->u = bin->data;
  93. d->len = bin->size;
  94. // I'd like to be more forceful on this check so that when
  95. // we run a second iteration of the decoder we are sure
  96. // that we're using the same binary. Unfortunately, I don't
  97. // think there's a value to base this assertion on.
  98. if(d->i < 0) {
  99. d->i = 0;
  100. } else {
  101. assert(d->i <= d->len && "mismatched binary lengths");
  102. }
  103. }
  104. void
  105. dec_destroy(ErlNifEnv* env, void* obj)
  106. {
  107. Decoder* d = (Decoder*) obj;
  108. if(d->st_data != NULL) {
  109. enif_free(d->st_data);
  110. }
  111. }
  112. ERL_NIF_TERM
  113. dec_error(Decoder* d, const char* atom)
  114. {
  115. ERL_NIF_TERM pos = enif_make_int(d->env, d->i+1);
  116. ERL_NIF_TERM msg = make_atom(d->env, atom);
  117. ERL_NIF_TERM ret = enif_make_tuple2(d->env, pos, msg);
  118. return enif_make_tuple2(d->env, d->atoms->atom_error, ret);
  119. }
  120. char
  121. dec_curr(Decoder* d)
  122. {
  123. return d->st_data[d->st_top-1];
  124. }
  125. int
  126. dec_top(Decoder* d)
  127. {
  128. return d->st_top;
  129. }
  130. void
  131. dec_push(Decoder* d, char val)
  132. {
  133. char* tmp;
  134. int new_sz;
  135. int i;
  136. if(d->st_top >= d->st_size) {
  137. new_sz = d->st_size + STACK_SIZE_INC;
  138. tmp = (char*) enif_alloc(new_sz * sizeof(char));
  139. memcpy(tmp, d->st_data, d->st_size * sizeof(char));
  140. enif_free(d->st_data);
  141. d->st_data = tmp;
  142. d->st_size = new_sz;
  143. for(i = d->st_top; i < d->st_size; i++) {
  144. d->st_data[i] = st_invalid;
  145. }
  146. }
  147. d->st_data[d->st_top++] = val;
  148. }
  149. void
  150. dec_pop(Decoder* d, char val)
  151. {
  152. assert(d->st_data[d->st_top-1] == val && "popped invalid state.");
  153. d->st_data[d->st_top-1] = st_invalid;
  154. d->st_top--;
  155. }
  156. int
  157. dec_string(Decoder* d, ERL_NIF_TERM* value)
  158. {
  159. int has_escape = 0;
  160. int num_escapes = 0;
  161. int st;
  162. int ulen;
  163. int ui;
  164. int hi;
  165. int lo;
  166. char* chrbuf;
  167. int chrpos;
  168. if(d->p[d->i] != '\"') {
  169. return 0;
  170. }
  171. d->i++;
  172. st = d->i;
  173. while(d->i < d->len) {
  174. if(d->u[d->i] < 0x20) {
  175. return 0;
  176. } else if(d->p[d->i] == '\"') {
  177. d->i++;
  178. goto parse;
  179. } else if(d->p[d->i] == '\\') {
  180. if(d->i+1 >= d->len) {
  181. return 0;
  182. }
  183. has_escape = 1;
  184. num_escapes += 1;
  185. d->i++;
  186. switch(d->p[d->i]) {
  187. case '\"':
  188. case '\\':
  189. case '/':
  190. case 'b':
  191. case 'f':
  192. case 'n':
  193. case 'r':
  194. case 't':
  195. d->i++;
  196. break;
  197. case 'u':
  198. hi = 0;
  199. lo = 0;
  200. d->i++;
  201. if(d->i + 4 >= d->len) {
  202. return 0;
  203. }
  204. hi = int_from_hex(&(d->u[d->i]));
  205. if(hi < 0) {
  206. return 0;
  207. }
  208. d->i += 4;
  209. if(hi >= 0xD800 && hi < 0xDC00) {
  210. if(d->i + 6 >= d->len) {
  211. return 0;
  212. }
  213. if(d->p[d->i++] != '\\') {
  214. return 0;
  215. } else if(d->p[d->i++] != 'u') {
  216. return 0;
  217. }
  218. lo = int_from_hex(&(d->u[d->i]));
  219. if(lo < 0) {
  220. return 0;
  221. }
  222. hi = unicode_from_pair(hi, lo);
  223. if(hi < 0) {
  224. return 0;
  225. }
  226. }
  227. hi = utf8_len(hi);
  228. if(hi < 0) {
  229. return 0;
  230. }
  231. if(lo == 0) {
  232. num_escapes += 5 - hi;
  233. } else {
  234. num_escapes += 11 - hi;
  235. }
  236. break;
  237. default:
  238. return 0;
  239. }
  240. } else if(d->u[d->i] < 0x80) {
  241. d->i++;
  242. } else {
  243. ulen = utf8_validate(&(d->u[d->i]), d->len - d->i);
  244. if(ulen < 0) {
  245. return 0;
  246. }
  247. d->i += ulen;
  248. }
  249. }
  250. // The goto above ensures that we only
  251. // hit this when a string is not terminated
  252. // correctly.
  253. return 0;
  254. parse:
  255. if(!has_escape) {
  256. *value = enif_make_sub_binary(d->env, d->arg, st, (d->i - st - 1));
  257. return 1;
  258. }
  259. hi = 0;
  260. lo = 0;
  261. ulen = (d->i - 1) - st - num_escapes;
  262. chrbuf = (char*) enif_make_new_binary(d->env, ulen, value);
  263. chrpos = 0;
  264. ui = st;
  265. while(ui < d->i - 1) {
  266. if(d->p[ui] != '\\') {
  267. chrbuf[chrpos++] = d->p[ui++];
  268. continue;
  269. }
  270. ui++;
  271. switch(d->p[ui]) {
  272. case '\"':
  273. case '\\':
  274. case '/':
  275. chrbuf[chrpos++] = d->p[ui];
  276. ui++;
  277. break;
  278. case 'b':
  279. chrbuf[chrpos++] = '\b';
  280. ui++;
  281. break;
  282. case 'f':
  283. chrbuf[chrpos++] = '\f';
  284. ui++;
  285. break;
  286. case 'n':
  287. chrbuf[chrpos++] = '\n';
  288. ui++;
  289. break;
  290. case 'r':
  291. chrbuf[chrpos++] = '\r';
  292. ui++;
  293. break;
  294. case 't':
  295. chrbuf[chrpos++] = '\t';
  296. ui++;
  297. break;
  298. case 'u':
  299. ui++;
  300. hi = int_from_hex(&(d->u[ui]));
  301. if(hi < 0) {
  302. return 0;
  303. }
  304. if(hi >= 0xD800 && hi < 0xDC00) {
  305. lo = int_from_hex(&(d->u[ui+6]));
  306. if(lo < 0) {
  307. return 0;
  308. }
  309. hi = unicode_from_pair(hi, lo);
  310. ui += 10;
  311. } else {
  312. ui += 4;
  313. }
  314. hi = unicode_to_utf8(hi, (unsigned char*) chrbuf+chrpos);
  315. if(hi < 0) {
  316. return 0;
  317. }
  318. chrpos += hi;
  319. break;
  320. default:
  321. return 0;
  322. }
  323. }
  324. return 1;
  325. }
  326. int
  327. dec_number(Decoder* d, ERL_NIF_TERM* value)
  328. {
  329. ERL_NIF_TERM num_type = d->atoms->atom_error;
  330. char state = nst_init;
  331. char nbuf[NUM_BUF_LEN];
  332. int st = d->i;
  333. int has_frac = 0;
  334. int has_exp = 0;
  335. double dval;
  336. long lval;
  337. while(d->i < d->len) {
  338. switch(state) {
  339. case nst_init:
  340. switch(d->p[d->i]) {
  341. case '-':
  342. state = nst_sign;
  343. d->i++;
  344. break;
  345. case '0':
  346. state = nst_frac0;
  347. d->i++;
  348. break;
  349. case '1':
  350. case '2':
  351. case '3':
  352. case '4':
  353. case '5':
  354. case '6':
  355. case '7':
  356. case '8':
  357. case '9':
  358. state = nst_mantissa;
  359. d->i++;
  360. break;
  361. default:
  362. return 0;
  363. }
  364. break;
  365. case nst_sign:
  366. switch(d->p[d->i]) {
  367. case '0':
  368. state = nst_frac0;
  369. d->i++;
  370. break;
  371. case '1':
  372. case '2':
  373. case '3':
  374. case '4':
  375. case '5':
  376. case '6':
  377. case '7':
  378. case '8':
  379. case '9':
  380. state = nst_mantissa;
  381. d->i++;
  382. break;
  383. default:
  384. return 0;
  385. }
  386. break;
  387. case nst_mantissa:
  388. switch(d->p[d->i]) {
  389. case '.':
  390. state = nst_frac1;
  391. d->i++;
  392. break;
  393. case 'e':
  394. case 'E':
  395. state = nst_esign;
  396. d->i++;
  397. break;
  398. case '0':
  399. case '1':
  400. case '2':
  401. case '3':
  402. case '4':
  403. case '5':
  404. case '6':
  405. case '7':
  406. case '8':
  407. case '9':
  408. d->i++;
  409. break;
  410. default:
  411. goto parse;
  412. }
  413. break;
  414. case nst_frac0:
  415. switch(d->p[d->i]) {
  416. case '.':
  417. state = nst_frac1;
  418. d->i++;
  419. break;
  420. case 'e':
  421. case 'E':
  422. state = nst_esign;
  423. d->i++;
  424. break;
  425. default:
  426. goto parse;
  427. }
  428. break;
  429. case nst_frac1:
  430. has_frac = 1;
  431. switch(d->p[d->i]) {
  432. case '0':
  433. case '1':
  434. case '2':
  435. case '3':
  436. case '4':
  437. case '5':
  438. case '6':
  439. case '7':
  440. case '8':
  441. case '9':
  442. state = nst_frac;
  443. d->i++;
  444. break;
  445. default:
  446. goto parse;
  447. }
  448. break;
  449. case nst_frac:
  450. switch(d->p[d->i]) {
  451. case 'e':
  452. case 'E':
  453. state = nst_esign;
  454. d->i++;
  455. break;
  456. case '0':
  457. case '1':
  458. case '2':
  459. case '3':
  460. case '4':
  461. case '5':
  462. case '6':
  463. case '7':
  464. case '8':
  465. case '9':
  466. d->i++;
  467. break;
  468. default:
  469. goto parse;
  470. }
  471. break;
  472. case nst_esign:
  473. has_exp = 1;
  474. switch(d->p[d->i]) {
  475. case '-':
  476. case '+':
  477. case '0':
  478. case '1':
  479. case '2':
  480. case '3':
  481. case '4':
  482. case '5':
  483. case '6':
  484. case '7':
  485. case '8':
  486. case '9':
  487. state = nst_edigit;
  488. d->i++;
  489. break;
  490. default:
  491. return 0;
  492. }
  493. break;
  494. case nst_edigit:
  495. switch(d->p[d->i]) {
  496. case '0':
  497. case '1':
  498. case '2':
  499. case '3':
  500. case '4':
  501. case '5':
  502. case '6':
  503. case '7':
  504. case '8':
  505. case '9':
  506. d->i++;
  507. break;
  508. default:
  509. goto parse;
  510. }
  511. break;
  512. default:
  513. return 0;
  514. }
  515. }
  516. parse:
  517. switch(state) {
  518. case nst_init:
  519. case nst_sign:
  520. case nst_frac1:
  521. case nst_esign:
  522. return 0;
  523. default:
  524. break;
  525. }
  526. errno = 0;
  527. if(d->i - st < NUM_BUF_LEN) {
  528. memset(nbuf, 0, NUM_BUF_LEN);
  529. memcpy(nbuf, &(d->p[st]), d->i - st);
  530. if(has_frac || has_exp) {
  531. dval = strtod(nbuf, NULL);
  532. if(errno != ERANGE) {
  533. *value = enif_make_double(d->env, dval);
  534. return 1;
  535. }
  536. } else {
  537. lval = strtol(nbuf, NULL, 10);
  538. if(errno != ERANGE) {
  539. *value = enif_make_int64(d->env, lval);
  540. return 1;
  541. }
  542. }
  543. }
  544. if(!has_frac && !has_exp) {
  545. num_type = d->atoms->atom_bignum;
  546. } else if(!has_frac && has_exp) {
  547. num_type = d->atoms->atom_bignum_e;
  548. } else {
  549. num_type = d->atoms->atom_bigdbl;
  550. }
  551. d->is_partial = 1;
  552. *value = enif_make_sub_binary(d->env, d->arg, st, d->i - st);
  553. *value = enif_make_tuple2(d->env, num_type, *value);
  554. return 1;
  555. }
  556. ERL_NIF_TERM
  557. make_empty_object(ErlNifEnv* env, int ret_map)
  558. {
  559. #if MAP_TYPE_PRESENT
  560. if(ret_map) {
  561. return enif_make_new_map(env);
  562. }
  563. #endif
  564. return enif_make_tuple1(env, enif_make_list(env, 0));
  565. }
  566. ERL_NIF_TERM
  567. make_array(ErlNifEnv* env, ERL_NIF_TERM list)
  568. {
  569. ERL_NIF_TERM ret = enif_make_list(env, 0);
  570. ERL_NIF_TERM item;
  571. while(enif_get_list_cell(env, list, &item, &list)) {
  572. ret = enif_make_list_cell(env, item, ret);
  573. }
  574. return ret;
  575. }
  576. ERL_NIF_TERM
  577. decode_init(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[])
  578. {
  579. Decoder* d;
  580. jiffy_st* st = (jiffy_st*) enif_priv_data(env);
  581. ERL_NIF_TERM tmp_argv[5];
  582. ERL_NIF_TERM opts;
  583. ERL_NIF_TERM val;
  584. if(argc != 2) {
  585. return enif_make_badarg(env);
  586. }
  587. d = dec_new(env);
  588. if(d == NULL) {
  589. return make_error(st, env, "internal_error");
  590. }
  591. tmp_argv[0] = argv[0];
  592. tmp_argv[1] = enif_make_resource(env, d);
  593. tmp_argv[2] = st->atom_error;
  594. tmp_argv[3] = enif_make_list(env, 0);
  595. tmp_argv[4] = enif_make_list(env, 0);
  596. enif_release_resource(d);
  597. opts = argv[1];
  598. if(!enif_is_list(env, opts)) {
  599. return enif_make_badarg(env);
  600. }
  601. while(enif_get_list_cell(env, opts, &val, &opts)) {
  602. if(get_bytes_per_iter(env, val, &(d->bytes_per_red))) {
  603. continue;
  604. } else if(get_bytes_per_red(env, val, &(d->bytes_per_red))) {
  605. continue;
  606. } else if(enif_compare(val, d->atoms->atom_return_maps) == 0) {
  607. #if MAP_TYPE_PRESENT
  608. d->return_maps = 1;
  609. #else
  610. return enif_make_badarg(env);
  611. #endif
  612. } else if(enif_compare(val, d->atoms->atom_return_trailer) == 0) {
  613. d->return_trailer = 1;
  614. } else if(enif_compare(val, d->atoms->atom_dedupe_keys) == 0) {
  615. d->dedupe_keys = 1;
  616. } else if(enif_compare(val, d->atoms->atom_use_nil) == 0) {
  617. d->null_term = d->atoms->atom_nil;
  618. } else if(get_null_term(env, val, &(d->null_term))) {
  619. continue;
  620. } else {
  621. return enif_make_badarg(env);
  622. }
  623. }
  624. return decode_iter(env, 5, tmp_argv);
  625. }
  626. ERL_NIF_TERM
  627. decode_iter(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[])
  628. {
  629. Decoder* d;
  630. jiffy_st* st = (jiffy_st*) enif_priv_data(env);
  631. ErlNifBinary bin;
  632. ERL_NIF_TERM objs;
  633. ERL_NIF_TERM curr;
  634. ERL_NIF_TERM val = argv[2];
  635. ERL_NIF_TERM trailer;
  636. ERL_NIF_TERM ret;
  637. size_t bytes_read = 0;
  638. if(argc != 5) {
  639. return enif_make_badarg(env);
  640. } else if(!enif_inspect_binary(env, argv[0], &bin)) {
  641. return enif_make_badarg(env);
  642. } else if(!enif_get_resource(env, argv[1], st->res_dec, (void**) &d)) {
  643. return enif_make_badarg(env);
  644. } else if(!enif_is_list(env, argv[3])) {
  645. return enif_make_badarg(env);
  646. } else if(!enif_is_list(env, argv[4])) {
  647. return enif_make_badarg(env);
  648. }
  649. dec_init(d, env, argv[0], &bin);
  650. objs = argv[3];
  651. curr = argv[4];
  652. while(d->i < bin.size) {
  653. if(should_yield(env, &bytes_read, d->bytes_per_red)) {
  654. return enif_make_tuple5(
  655. env,
  656. st->atom_iter,
  657. argv[1],
  658. val,
  659. objs,
  660. curr
  661. );
  662. }
  663. bytes_read += 1;
  664. switch(dec_curr(d)) {
  665. case st_value:
  666. switch(d->p[d->i]) {
  667. case ' ':
  668. case '\n':
  669. case '\r':
  670. case '\t':
  671. d->i++;
  672. break;
  673. case 'n':
  674. if(d->i + 3 >= d->len) {
  675. ret = dec_error(d, "invalid_literal");
  676. goto done;
  677. }
  678. if(memcmp(&(d->p[d->i]), "null", 4) != 0) {
  679. ret = dec_error(d, "invalid_literal");
  680. goto done;
  681. }
  682. val = d->null_term;
  683. dec_pop(d, st_value);
  684. d->i += 4;
  685. break;
  686. case 't':
  687. if(d->i + 3 >= d->len) {
  688. ret = dec_error(d, "invalid_literal");
  689. goto done;
  690. }
  691. if(memcmp(&(d->p[d->i]), "true", 4) != 0) {
  692. ret = dec_error(d, "invalid_literal");
  693. goto done;
  694. }
  695. val = d->atoms->atom_true;
  696. dec_pop(d, st_value);
  697. d->i += 4;
  698. break;
  699. case 'f':
  700. if(d->i + 4 >= bin.size) {
  701. ret = dec_error(d, "invalid_literal");
  702. goto done;
  703. }
  704. if(memcmp(&(d->p[d->i]), "false", 5) != 0) {
  705. ret = dec_error(d, "invalid_literal");
  706. goto done;
  707. }
  708. val = d->atoms->atom_false;
  709. dec_pop(d, st_value);
  710. d->i += 5;
  711. break;
  712. case '\"':
  713. if(!dec_string(d, &val)) {
  714. ret = dec_error(d, "invalid_string");
  715. goto done;
  716. }
  717. dec_pop(d, st_value);
  718. break;
  719. case '-':
  720. case '0':
  721. case '1':
  722. case '2':
  723. case '3':
  724. case '4':
  725. case '5':
  726. case '6':
  727. case '7':
  728. case '8':
  729. case '9':
  730. if(!dec_number(d, &val)) {
  731. ret = dec_error(d, "invalid_number");
  732. goto done;
  733. }
  734. dec_pop(d, st_value);
  735. break;
  736. case '{':
  737. dec_push(d, st_object);
  738. dec_push(d, st_key);
  739. objs = enif_make_list_cell(env, curr, objs);
  740. curr = enif_make_list(env, 0);
  741. d->i++;
  742. break;
  743. case '[':
  744. dec_push(d, st_array);
  745. dec_push(d, st_value);
  746. objs = enif_make_list_cell(env, curr, objs);
  747. curr = enif_make_list(env, 0);
  748. d->i++;
  749. break;
  750. case ']':
  751. if(!enif_is_empty_list(env, curr)) {
  752. ret = dec_error(d, "invalid_json");
  753. goto done;
  754. }
  755. dec_pop(d, st_value);
  756. if(dec_curr(d) != st_array) {
  757. ret = dec_error(d, "invalid_json");
  758. goto done;
  759. }
  760. dec_pop(d, st_array);
  761. dec_pop(d, st_value);
  762. val = curr; // curr is []
  763. if(!enif_get_list_cell(env, objs, &curr, &objs)) {
  764. ret = dec_error(d, "internal_error");
  765. goto done;
  766. }
  767. d->i++;
  768. break;
  769. default:
  770. ret = dec_error(d, "invalid_json");
  771. goto done;
  772. }
  773. if(dec_top(d) == 0) {
  774. dec_push(d, st_done);
  775. } else if(dec_curr(d) != st_value && dec_curr(d) != st_key) {
  776. dec_push(d, st_comma);
  777. curr = enif_make_list_cell(env, val, curr);
  778. }
  779. break;
  780. case st_key:
  781. switch(d->p[d->i]) {
  782. case ' ':
  783. case '\n':
  784. case '\r':
  785. case '\t':
  786. d->i++;
  787. break;
  788. case '\"':
  789. if(!dec_string(d, &val)) {
  790. ret = dec_error(d, "invalid_string");
  791. goto done;
  792. }
  793. dec_pop(d, st_key);
  794. dec_push(d, st_colon);
  795. curr = enif_make_list_cell(env, val, curr);
  796. break;
  797. case '}':
  798. if(!enif_is_empty_list(env, curr)) {
  799. ret = dec_error(d, "invalid_json");
  800. goto done;
  801. }
  802. dec_pop(d, st_key);
  803. dec_pop(d, st_object);
  804. dec_pop(d, st_value);
  805. val = make_empty_object(env, d->return_maps);
  806. if(!enif_get_list_cell(env, objs, &curr, &objs)) {
  807. ret = dec_error(d, "internal_error");
  808. goto done;
  809. }
  810. if(dec_top(d) == 0) {
  811. dec_push(d, st_done);
  812. } else {
  813. dec_push(d, st_comma);
  814. curr = enif_make_list_cell(env, val, curr);
  815. }
  816. d->i++;
  817. break;
  818. default:
  819. ret = dec_error(d, "invalid_json");
  820. goto done;
  821. }
  822. break;
  823. case st_colon:
  824. switch(d->p[d->i]) {
  825. case ' ':
  826. case '\n':
  827. case '\r':
  828. case '\t':
  829. d->i++;
  830. break;
  831. case ':':
  832. dec_pop(d, st_colon);
  833. dec_push(d, st_value);
  834. d->i++;
  835. break;
  836. default:
  837. ret = dec_error(d, "invalid_json");
  838. goto done;
  839. }
  840. break;
  841. case st_comma:
  842. switch(d->p[d->i]) {
  843. case ' ':
  844. case '\n':
  845. case '\r':
  846. case '\t':
  847. d->i++;
  848. break;
  849. case ',':
  850. dec_pop(d, st_comma);
  851. switch(dec_curr(d)) {
  852. case st_object:
  853. dec_push(d, st_key);
  854. break;
  855. case st_array:
  856. dec_push(d, st_value);
  857. break;
  858. default:
  859. ret = dec_error(d, "internal_error");
  860. goto done;
  861. }
  862. d->i++;
  863. break;
  864. case '}':
  865. dec_pop(d, st_comma);
  866. if(dec_curr(d) != st_object) {
  867. ret = dec_error(d, "invalid_json");
  868. goto done;
  869. }
  870. dec_pop(d, st_object);
  871. dec_pop(d, st_value);
  872. if(!make_object(env, curr, &val,
  873. d->return_maps, d->dedupe_keys)) {
  874. ret = dec_error(d, "internal_object_error");
  875. goto done;
  876. }
  877. if(!enif_get_list_cell(env, objs, &curr, &objs)) {
  878. ret = dec_error(d, "internal_error");
  879. goto done;
  880. }
  881. if(dec_top(d) > 0) {
  882. dec_push(d, st_comma);
  883. curr = enif_make_list_cell(env, val, curr);
  884. } else {
  885. dec_push(d, st_done);
  886. }
  887. d->i++;
  888. break;
  889. case ']':
  890. dec_pop(d, st_comma);
  891. if(dec_curr(d) != st_array) {
  892. ret = dec_error(d, "invalid_json");
  893. goto done;
  894. }
  895. dec_pop(d, st_array);
  896. dec_pop(d, st_value);
  897. val = make_array(env, curr);
  898. if(!enif_get_list_cell(env, objs, &curr, &objs)) {
  899. ret = dec_error(d, "internal_error");
  900. goto done;
  901. }
  902. if(dec_top(d) > 0) {
  903. dec_push(d, st_comma);
  904. curr = enif_make_list_cell(env, val, curr);
  905. } else {
  906. dec_push(d, st_done);
  907. }
  908. d->i++;
  909. break;
  910. default:
  911. ret = dec_error(d, "invalid_json");
  912. goto done;
  913. }
  914. break;
  915. case st_done:
  916. switch(d->p[d->i]) {
  917. case ' ':
  918. case '\n':
  919. case '\r':
  920. case '\t':
  921. d->i++;
  922. break;
  923. default:
  924. goto decode_done;
  925. }
  926. break;
  927. default:
  928. ret = dec_error(d, "invalid_internal_state");
  929. goto done;
  930. }
  931. }
  932. decode_done:
  933. if(d->i < bin.size && d->return_trailer) {
  934. trailer = enif_make_sub_binary(env, argv[0], d->i, bin.size - d->i);
  935. val = enif_make_tuple3(env, d->atoms->atom_has_trailer, val, trailer);
  936. } else if(d->i < bin.size) {
  937. ret = dec_error(d, "invalid_trailing_data");
  938. goto done;
  939. }
  940. if(dec_curr(d) != st_done) {
  941. ret = dec_error(d, "truncated_json");
  942. } else if(d->is_partial) {
  943. ret = enif_make_tuple2(env, d->atoms->atom_partial, val);
  944. } else {
  945. ret = val;
  946. }
  947. done:
  948. return ret;
  949. }