summaryrefslogtreecommitdiff
path: root/upb/json/parser.h
blob: 51578f2615e71d8f3a456ba874c26fd06e9aaf08 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
/*
 * upb - a minimalist implementation of protocol buffers.
 *
 * Copyright (c) 2014 Google Inc.  See LICENSE for details.
 * Author: Josh Haberman <jhaberman@gmail.com>
 *
 * upb::json::Parser can parse JSON according to a specific schema.
 * Support for parsing arbitrary JSON (schema-less) will be added later.
 */

#ifndef UPB_JSON_PARSER_H_
#define UPB_JSON_PARSER_H_

#include "upb/sink.h"

#ifdef __cplusplus
namespace upb {
namespace json {
class Parser;
}  // namespace json
}  // namespace upb
#endif

UPB_DECLARE_TYPE(upb::json::Parser, upb_json_parser);

// Internal-only struct used by the parser.
typedef struct {
 UPB_PRIVATE_FOR_CPP
  upb_sink sink;
  const upb_msgdef *m;
  const upb_fielddef *f;
} upb_jsonparser_frame;


/* upb::json::Parser **********************************************************/

#define UPB_JSON_MAX_DEPTH 64

// Parses an incoming BytesStream, pushing the results to the destination sink.
UPB_DEFINE_CLASS0(upb::json::Parser,
 public:
  Parser(Status* status);
  ~Parser();

  // Resets the state of the printer, so that it will expect to begin a new
  // document.
  void Reset();

  // Resets the output pointer which will serve as our closure.  Implies
  // Reset().
  void ResetOutput(Sink* output);

  // The input to the printer.
  BytesSink* input();
,
UPB_DEFINE_STRUCT0(upb_json_parser,
  upb_byteshandler input_handler_;
  upb_bytessink input_;

  // Stack to track the JSON scopes we are in.
  upb_jsonparser_frame stack[UPB_JSON_MAX_DEPTH];
  upb_jsonparser_frame *top;
  upb_jsonparser_frame *limit;

  upb_status *status;

  // Ragel's internal parsing stack for the parsing state machine.
  int current_state;
  int parser_stack[UPB_JSON_MAX_DEPTH];
  int parser_top;

  // The handle for the current buffer.
  const upb_bufhandle *handle;

  // Accumulate buffer.  See details in parser.rl.
  const char *accumulated;
  size_t accumulated_len;
  char *accumulate_buf;
  size_t accumulate_buf_size;

  // Multi-part text data.  See details in parser.rl.
  int multipart_state;
  upb_selector_t string_selector;

  // Input capture.  See details in parser.rl.
  const char *capture;

  // Intermediate result of parsing a unicode escape sequence.
  uint32_t digit;
));

UPB_BEGIN_EXTERN_C

void upb_json_parser_init(upb_json_parser *p, upb_status *status);
void upb_json_parser_uninit(upb_json_parser *p);
void upb_json_parser_reset(upb_json_parser *p);
void upb_json_parser_resetoutput(upb_json_parser *p, upb_sink *output);
upb_bytessink *upb_json_parser_input(upb_json_parser *p);

UPB_END_EXTERN_C

#ifdef __cplusplus

namespace upb {
namespace json {
inline Parser::Parser(Status* status) { upb_json_parser_init(this, status); }
inline Parser::~Parser() { upb_json_parser_uninit(this); }
inline void Parser::Reset() { upb_json_parser_reset(this); }
inline void Parser::ResetOutput(Sink* output) {
  upb_json_parser_resetoutput(this, output);
}
inline BytesSink* Parser::input() {
  return upb_json_parser_input(this);
}
}  // namespace json
}  // namespace upb

#endif


#endif  // UPB_JSON_PARSER_H_
generated by cgit on debian on lair
contact matthew@masot.net with questions or feedback