xref: /freebsd/contrib/libyaml/src/loader.c (revision 0f5c86ddb0257f4b7620f1d8e898289be30b19bf)
1*0f5c86ddSBaptiste Daroussin 
2*0f5c86ddSBaptiste Daroussin #include "yaml_private.h"
3*0f5c86ddSBaptiste Daroussin 
4*0f5c86ddSBaptiste Daroussin /*
5*0f5c86ddSBaptiste Daroussin  * API functions.
6*0f5c86ddSBaptiste Daroussin  */
7*0f5c86ddSBaptiste Daroussin 
8*0f5c86ddSBaptiste Daroussin YAML_DECLARE(int)
9*0f5c86ddSBaptiste Daroussin yaml_parser_load(yaml_parser_t *parser, yaml_document_t *document);
10*0f5c86ddSBaptiste Daroussin 
11*0f5c86ddSBaptiste Daroussin /*
12*0f5c86ddSBaptiste Daroussin  * Error handling.
13*0f5c86ddSBaptiste Daroussin  */
14*0f5c86ddSBaptiste Daroussin 
15*0f5c86ddSBaptiste Daroussin static int
16*0f5c86ddSBaptiste Daroussin yaml_parser_set_composer_error(yaml_parser_t *parser,
17*0f5c86ddSBaptiste Daroussin         const char *problem, yaml_mark_t problem_mark);
18*0f5c86ddSBaptiste Daroussin 
19*0f5c86ddSBaptiste Daroussin static int
20*0f5c86ddSBaptiste Daroussin yaml_parser_set_composer_error_context(yaml_parser_t *parser,
21*0f5c86ddSBaptiste Daroussin         const char *context, yaml_mark_t context_mark,
22*0f5c86ddSBaptiste Daroussin         const char *problem, yaml_mark_t problem_mark);
23*0f5c86ddSBaptiste Daroussin 
24*0f5c86ddSBaptiste Daroussin 
25*0f5c86ddSBaptiste Daroussin /*
26*0f5c86ddSBaptiste Daroussin  * Alias handling.
27*0f5c86ddSBaptiste Daroussin  */
28*0f5c86ddSBaptiste Daroussin 
29*0f5c86ddSBaptiste Daroussin static int
30*0f5c86ddSBaptiste Daroussin yaml_parser_register_anchor(yaml_parser_t *parser,
31*0f5c86ddSBaptiste Daroussin         int index, yaml_char_t *anchor);
32*0f5c86ddSBaptiste Daroussin 
33*0f5c86ddSBaptiste Daroussin /*
34*0f5c86ddSBaptiste Daroussin  * Clean up functions.
35*0f5c86ddSBaptiste Daroussin  */
36*0f5c86ddSBaptiste Daroussin 
37*0f5c86ddSBaptiste Daroussin static void
38*0f5c86ddSBaptiste Daroussin yaml_parser_delete_aliases(yaml_parser_t *parser);
39*0f5c86ddSBaptiste Daroussin 
40*0f5c86ddSBaptiste Daroussin /*
41*0f5c86ddSBaptiste Daroussin  * Document loading context.
42*0f5c86ddSBaptiste Daroussin  */
43*0f5c86ddSBaptiste Daroussin struct loader_ctx {
44*0f5c86ddSBaptiste Daroussin     int *start;
45*0f5c86ddSBaptiste Daroussin     int *end;
46*0f5c86ddSBaptiste Daroussin     int *top;
47*0f5c86ddSBaptiste Daroussin };
48*0f5c86ddSBaptiste Daroussin 
49*0f5c86ddSBaptiste Daroussin /*
50*0f5c86ddSBaptiste Daroussin  * Composer functions.
51*0f5c86ddSBaptiste Daroussin  */
52*0f5c86ddSBaptiste Daroussin static int
53*0f5c86ddSBaptiste Daroussin yaml_parser_load_nodes(yaml_parser_t *parser, struct loader_ctx *ctx);
54*0f5c86ddSBaptiste Daroussin 
55*0f5c86ddSBaptiste Daroussin static int
56*0f5c86ddSBaptiste Daroussin yaml_parser_load_document(yaml_parser_t *parser, yaml_event_t *event);
57*0f5c86ddSBaptiste Daroussin 
58*0f5c86ddSBaptiste Daroussin static int
59*0f5c86ddSBaptiste Daroussin yaml_parser_load_alias(yaml_parser_t *parser, yaml_event_t *event,
60*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx);
61*0f5c86ddSBaptiste Daroussin 
62*0f5c86ddSBaptiste Daroussin static int
63*0f5c86ddSBaptiste Daroussin yaml_parser_load_scalar(yaml_parser_t *parser, yaml_event_t *event,
64*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx);
65*0f5c86ddSBaptiste Daroussin 
66*0f5c86ddSBaptiste Daroussin static int
67*0f5c86ddSBaptiste Daroussin yaml_parser_load_sequence(yaml_parser_t *parser, yaml_event_t *event,
68*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx);
69*0f5c86ddSBaptiste Daroussin 
70*0f5c86ddSBaptiste Daroussin static int
71*0f5c86ddSBaptiste Daroussin yaml_parser_load_mapping(yaml_parser_t *parser, yaml_event_t *event,
72*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx);
73*0f5c86ddSBaptiste Daroussin 
74*0f5c86ddSBaptiste Daroussin static int
75*0f5c86ddSBaptiste Daroussin yaml_parser_load_sequence_end(yaml_parser_t *parser, yaml_event_t *event,
76*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx);
77*0f5c86ddSBaptiste Daroussin 
78*0f5c86ddSBaptiste Daroussin static int
79*0f5c86ddSBaptiste Daroussin yaml_parser_load_mapping_end(yaml_parser_t *parser, yaml_event_t *event,
80*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx);
81*0f5c86ddSBaptiste Daroussin 
82*0f5c86ddSBaptiste Daroussin /*
83*0f5c86ddSBaptiste Daroussin  * Load the next document of the stream.
84*0f5c86ddSBaptiste Daroussin  */
85*0f5c86ddSBaptiste Daroussin 
86*0f5c86ddSBaptiste Daroussin YAML_DECLARE(int)
yaml_parser_load(yaml_parser_t * parser,yaml_document_t * document)87*0f5c86ddSBaptiste Daroussin yaml_parser_load(yaml_parser_t *parser, yaml_document_t *document)
88*0f5c86ddSBaptiste Daroussin {
89*0f5c86ddSBaptiste Daroussin     yaml_event_t event;
90*0f5c86ddSBaptiste Daroussin 
91*0f5c86ddSBaptiste Daroussin     assert(parser);     /* Non-NULL parser object is expected. */
92*0f5c86ddSBaptiste Daroussin     assert(document);   /* Non-NULL document object is expected. */
93*0f5c86ddSBaptiste Daroussin 
94*0f5c86ddSBaptiste Daroussin     memset(document, 0, sizeof(yaml_document_t));
95*0f5c86ddSBaptiste Daroussin     if (!STACK_INIT(parser, document->nodes, yaml_node_t*))
96*0f5c86ddSBaptiste Daroussin         goto error;
97*0f5c86ddSBaptiste Daroussin 
98*0f5c86ddSBaptiste Daroussin     if (!parser->stream_start_produced) {
99*0f5c86ddSBaptiste Daroussin         if (!yaml_parser_parse(parser, &event)) goto error;
100*0f5c86ddSBaptiste Daroussin         assert(event.type == YAML_STREAM_START_EVENT);
101*0f5c86ddSBaptiste Daroussin                         /* STREAM-START is expected. */
102*0f5c86ddSBaptiste Daroussin     }
103*0f5c86ddSBaptiste Daroussin 
104*0f5c86ddSBaptiste Daroussin     if (parser->stream_end_produced) {
105*0f5c86ddSBaptiste Daroussin         return 1;
106*0f5c86ddSBaptiste Daroussin     }
107*0f5c86ddSBaptiste Daroussin 
108*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_parse(parser, &event)) goto error;
109*0f5c86ddSBaptiste Daroussin     if (event.type == YAML_STREAM_END_EVENT) {
110*0f5c86ddSBaptiste Daroussin         return 1;
111*0f5c86ddSBaptiste Daroussin     }
112*0f5c86ddSBaptiste Daroussin 
113*0f5c86ddSBaptiste Daroussin     if (!STACK_INIT(parser, parser->aliases, yaml_alias_data_t*))
114*0f5c86ddSBaptiste Daroussin         goto error;
115*0f5c86ddSBaptiste Daroussin 
116*0f5c86ddSBaptiste Daroussin     parser->document = document;
117*0f5c86ddSBaptiste Daroussin 
118*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_load_document(parser, &event)) goto error;
119*0f5c86ddSBaptiste Daroussin 
120*0f5c86ddSBaptiste Daroussin     yaml_parser_delete_aliases(parser);
121*0f5c86ddSBaptiste Daroussin     parser->document = NULL;
122*0f5c86ddSBaptiste Daroussin 
123*0f5c86ddSBaptiste Daroussin     return 1;
124*0f5c86ddSBaptiste Daroussin 
125*0f5c86ddSBaptiste Daroussin error:
126*0f5c86ddSBaptiste Daroussin 
127*0f5c86ddSBaptiste Daroussin     yaml_parser_delete_aliases(parser);
128*0f5c86ddSBaptiste Daroussin     yaml_document_delete(document);
129*0f5c86ddSBaptiste Daroussin     parser->document = NULL;
130*0f5c86ddSBaptiste Daroussin 
131*0f5c86ddSBaptiste Daroussin     return 0;
132*0f5c86ddSBaptiste Daroussin }
133*0f5c86ddSBaptiste Daroussin 
134*0f5c86ddSBaptiste Daroussin /*
135*0f5c86ddSBaptiste Daroussin  * Set composer error.
136*0f5c86ddSBaptiste Daroussin  */
137*0f5c86ddSBaptiste Daroussin 
138*0f5c86ddSBaptiste Daroussin static int
yaml_parser_set_composer_error(yaml_parser_t * parser,const char * problem,yaml_mark_t problem_mark)139*0f5c86ddSBaptiste Daroussin yaml_parser_set_composer_error(yaml_parser_t *parser,
140*0f5c86ddSBaptiste Daroussin         const char *problem, yaml_mark_t problem_mark)
141*0f5c86ddSBaptiste Daroussin {
142*0f5c86ddSBaptiste Daroussin     parser->error = YAML_COMPOSER_ERROR;
143*0f5c86ddSBaptiste Daroussin     parser->problem = problem;
144*0f5c86ddSBaptiste Daroussin     parser->problem_mark = problem_mark;
145*0f5c86ddSBaptiste Daroussin 
146*0f5c86ddSBaptiste Daroussin     return 0;
147*0f5c86ddSBaptiste Daroussin }
148*0f5c86ddSBaptiste Daroussin 
149*0f5c86ddSBaptiste Daroussin /*
150*0f5c86ddSBaptiste Daroussin  * Set composer error with context.
151*0f5c86ddSBaptiste Daroussin  */
152*0f5c86ddSBaptiste Daroussin 
153*0f5c86ddSBaptiste Daroussin static int
yaml_parser_set_composer_error_context(yaml_parser_t * parser,const char * context,yaml_mark_t context_mark,const char * problem,yaml_mark_t problem_mark)154*0f5c86ddSBaptiste Daroussin yaml_parser_set_composer_error_context(yaml_parser_t *parser,
155*0f5c86ddSBaptiste Daroussin         const char *context, yaml_mark_t context_mark,
156*0f5c86ddSBaptiste Daroussin         const char *problem, yaml_mark_t problem_mark)
157*0f5c86ddSBaptiste Daroussin {
158*0f5c86ddSBaptiste Daroussin     parser->error = YAML_COMPOSER_ERROR;
159*0f5c86ddSBaptiste Daroussin     parser->context = context;
160*0f5c86ddSBaptiste Daroussin     parser->context_mark = context_mark;
161*0f5c86ddSBaptiste Daroussin     parser->problem = problem;
162*0f5c86ddSBaptiste Daroussin     parser->problem_mark = problem_mark;
163*0f5c86ddSBaptiste Daroussin 
164*0f5c86ddSBaptiste Daroussin     return 0;
165*0f5c86ddSBaptiste Daroussin }
166*0f5c86ddSBaptiste Daroussin 
167*0f5c86ddSBaptiste Daroussin /*
168*0f5c86ddSBaptiste Daroussin  * Delete the stack of aliases.
169*0f5c86ddSBaptiste Daroussin  */
170*0f5c86ddSBaptiste Daroussin 
171*0f5c86ddSBaptiste Daroussin static void
yaml_parser_delete_aliases(yaml_parser_t * parser)172*0f5c86ddSBaptiste Daroussin yaml_parser_delete_aliases(yaml_parser_t *parser)
173*0f5c86ddSBaptiste Daroussin {
174*0f5c86ddSBaptiste Daroussin     while (!STACK_EMPTY(parser, parser->aliases)) {
175*0f5c86ddSBaptiste Daroussin         yaml_free(POP(parser, parser->aliases).anchor);
176*0f5c86ddSBaptiste Daroussin     }
177*0f5c86ddSBaptiste Daroussin     STACK_DEL(parser, parser->aliases);
178*0f5c86ddSBaptiste Daroussin }
179*0f5c86ddSBaptiste Daroussin 
180*0f5c86ddSBaptiste Daroussin /*
181*0f5c86ddSBaptiste Daroussin  * Compose a document object.
182*0f5c86ddSBaptiste Daroussin  */
183*0f5c86ddSBaptiste Daroussin 
184*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_document(yaml_parser_t * parser,yaml_event_t * event)185*0f5c86ddSBaptiste Daroussin yaml_parser_load_document(yaml_parser_t *parser, yaml_event_t *event)
186*0f5c86ddSBaptiste Daroussin {
187*0f5c86ddSBaptiste Daroussin     struct loader_ctx ctx = { NULL, NULL, NULL };
188*0f5c86ddSBaptiste Daroussin 
189*0f5c86ddSBaptiste Daroussin     assert(event->type == YAML_DOCUMENT_START_EVENT);
190*0f5c86ddSBaptiste Daroussin                         /* DOCUMENT-START is expected. */
191*0f5c86ddSBaptiste Daroussin 
192*0f5c86ddSBaptiste Daroussin     parser->document->version_directive
193*0f5c86ddSBaptiste Daroussin         = event->data.document_start.version_directive;
194*0f5c86ddSBaptiste Daroussin     parser->document->tag_directives.start
195*0f5c86ddSBaptiste Daroussin         = event->data.document_start.tag_directives.start;
196*0f5c86ddSBaptiste Daroussin     parser->document->tag_directives.end
197*0f5c86ddSBaptiste Daroussin         = event->data.document_start.tag_directives.end;
198*0f5c86ddSBaptiste Daroussin     parser->document->start_implicit
199*0f5c86ddSBaptiste Daroussin         = event->data.document_start.implicit;
200*0f5c86ddSBaptiste Daroussin     parser->document->start_mark = event->start_mark;
201*0f5c86ddSBaptiste Daroussin 
202*0f5c86ddSBaptiste Daroussin     if (!STACK_INIT(parser, ctx, int*)) return 0;
203*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_load_nodes(parser, &ctx)) {
204*0f5c86ddSBaptiste Daroussin         STACK_DEL(parser, ctx);
205*0f5c86ddSBaptiste Daroussin         return 0;
206*0f5c86ddSBaptiste Daroussin     }
207*0f5c86ddSBaptiste Daroussin     STACK_DEL(parser, ctx);
208*0f5c86ddSBaptiste Daroussin 
209*0f5c86ddSBaptiste Daroussin     return 1;
210*0f5c86ddSBaptiste Daroussin }
211*0f5c86ddSBaptiste Daroussin 
212*0f5c86ddSBaptiste Daroussin /*
213*0f5c86ddSBaptiste Daroussin  * Compose a node tree.
214*0f5c86ddSBaptiste Daroussin  */
215*0f5c86ddSBaptiste Daroussin 
216*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_nodes(yaml_parser_t * parser,struct loader_ctx * ctx)217*0f5c86ddSBaptiste Daroussin yaml_parser_load_nodes(yaml_parser_t *parser, struct loader_ctx *ctx)
218*0f5c86ddSBaptiste Daroussin {
219*0f5c86ddSBaptiste Daroussin     yaml_event_t event;
220*0f5c86ddSBaptiste Daroussin 
221*0f5c86ddSBaptiste Daroussin     do {
222*0f5c86ddSBaptiste Daroussin         if (!yaml_parser_parse(parser, &event)) return 0;
223*0f5c86ddSBaptiste Daroussin 
224*0f5c86ddSBaptiste Daroussin         switch (event.type) {
225*0f5c86ddSBaptiste Daroussin             case YAML_ALIAS_EVENT:
226*0f5c86ddSBaptiste Daroussin                 if (!yaml_parser_load_alias(parser, &event, ctx)) return 0;
227*0f5c86ddSBaptiste Daroussin                 break;
228*0f5c86ddSBaptiste Daroussin             case YAML_SCALAR_EVENT:
229*0f5c86ddSBaptiste Daroussin                 if (!yaml_parser_load_scalar(parser, &event, ctx)) return 0;
230*0f5c86ddSBaptiste Daroussin                 break;
231*0f5c86ddSBaptiste Daroussin             case YAML_SEQUENCE_START_EVENT:
232*0f5c86ddSBaptiste Daroussin                 if (!yaml_parser_load_sequence(parser, &event, ctx)) return 0;
233*0f5c86ddSBaptiste Daroussin                 break;
234*0f5c86ddSBaptiste Daroussin             case YAML_SEQUENCE_END_EVENT:
235*0f5c86ddSBaptiste Daroussin                 if (!yaml_parser_load_sequence_end(parser, &event, ctx))
236*0f5c86ddSBaptiste Daroussin                     return 0;
237*0f5c86ddSBaptiste Daroussin                 break;
238*0f5c86ddSBaptiste Daroussin             case YAML_MAPPING_START_EVENT:
239*0f5c86ddSBaptiste Daroussin                 if (!yaml_parser_load_mapping(parser, &event, ctx)) return 0;
240*0f5c86ddSBaptiste Daroussin                 break;
241*0f5c86ddSBaptiste Daroussin             case YAML_MAPPING_END_EVENT:
242*0f5c86ddSBaptiste Daroussin                 if (!yaml_parser_load_mapping_end(parser, &event, ctx))
243*0f5c86ddSBaptiste Daroussin                     return 0;
244*0f5c86ddSBaptiste Daroussin                 break;
245*0f5c86ddSBaptiste Daroussin             default:
246*0f5c86ddSBaptiste Daroussin                 assert(0);  /* Could not happen. */
247*0f5c86ddSBaptiste Daroussin                 return 0;
248*0f5c86ddSBaptiste Daroussin             case YAML_DOCUMENT_END_EVENT:
249*0f5c86ddSBaptiste Daroussin                 break;
250*0f5c86ddSBaptiste Daroussin         }
251*0f5c86ddSBaptiste Daroussin     } while (event.type != YAML_DOCUMENT_END_EVENT);
252*0f5c86ddSBaptiste Daroussin 
253*0f5c86ddSBaptiste Daroussin     parser->document->end_implicit = event.data.document_end.implicit;
254*0f5c86ddSBaptiste Daroussin     parser->document->end_mark = event.end_mark;
255*0f5c86ddSBaptiste Daroussin 
256*0f5c86ddSBaptiste Daroussin     return 1;
257*0f5c86ddSBaptiste Daroussin }
258*0f5c86ddSBaptiste Daroussin 
259*0f5c86ddSBaptiste Daroussin /*
260*0f5c86ddSBaptiste Daroussin  * Add an anchor.
261*0f5c86ddSBaptiste Daroussin  */
262*0f5c86ddSBaptiste Daroussin 
263*0f5c86ddSBaptiste Daroussin static int
yaml_parser_register_anchor(yaml_parser_t * parser,int index,yaml_char_t * anchor)264*0f5c86ddSBaptiste Daroussin yaml_parser_register_anchor(yaml_parser_t *parser,
265*0f5c86ddSBaptiste Daroussin         int index, yaml_char_t *anchor)
266*0f5c86ddSBaptiste Daroussin {
267*0f5c86ddSBaptiste Daroussin     yaml_alias_data_t data;
268*0f5c86ddSBaptiste Daroussin     yaml_alias_data_t *alias_data;
269*0f5c86ddSBaptiste Daroussin 
270*0f5c86ddSBaptiste Daroussin     if (!anchor) return 1;
271*0f5c86ddSBaptiste Daroussin 
272*0f5c86ddSBaptiste Daroussin     data.anchor = anchor;
273*0f5c86ddSBaptiste Daroussin     data.index = index;
274*0f5c86ddSBaptiste Daroussin     data.mark = parser->document->nodes.start[index-1].start_mark;
275*0f5c86ddSBaptiste Daroussin 
276*0f5c86ddSBaptiste Daroussin     for (alias_data = parser->aliases.start;
277*0f5c86ddSBaptiste Daroussin             alias_data != parser->aliases.top; alias_data ++) {
278*0f5c86ddSBaptiste Daroussin         if (strcmp((char *)alias_data->anchor, (char *)anchor) == 0) {
279*0f5c86ddSBaptiste Daroussin             yaml_free(anchor);
280*0f5c86ddSBaptiste Daroussin             return yaml_parser_set_composer_error_context(parser,
281*0f5c86ddSBaptiste Daroussin                     "found duplicate anchor; first occurrence",
282*0f5c86ddSBaptiste Daroussin                     alias_data->mark, "second occurrence", data.mark);
283*0f5c86ddSBaptiste Daroussin         }
284*0f5c86ddSBaptiste Daroussin     }
285*0f5c86ddSBaptiste Daroussin 
286*0f5c86ddSBaptiste Daroussin     if (!PUSH(parser, parser->aliases, data)) {
287*0f5c86ddSBaptiste Daroussin         yaml_free(anchor);
288*0f5c86ddSBaptiste Daroussin         return 0;
289*0f5c86ddSBaptiste Daroussin     }
290*0f5c86ddSBaptiste Daroussin 
291*0f5c86ddSBaptiste Daroussin     return 1;
292*0f5c86ddSBaptiste Daroussin }
293*0f5c86ddSBaptiste Daroussin 
294*0f5c86ddSBaptiste Daroussin /*
295*0f5c86ddSBaptiste Daroussin  * Compose node into its parent in the stree.
296*0f5c86ddSBaptiste Daroussin  */
297*0f5c86ddSBaptiste Daroussin 
298*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_node_add(yaml_parser_t * parser,struct loader_ctx * ctx,int index)299*0f5c86ddSBaptiste Daroussin yaml_parser_load_node_add(yaml_parser_t *parser, struct loader_ctx *ctx,
300*0f5c86ddSBaptiste Daroussin         int index)
301*0f5c86ddSBaptiste Daroussin {
302*0f5c86ddSBaptiste Daroussin     struct yaml_node_s *parent;
303*0f5c86ddSBaptiste Daroussin     int parent_index;
304*0f5c86ddSBaptiste Daroussin 
305*0f5c86ddSBaptiste Daroussin     if (STACK_EMPTY(parser, *ctx)) {
306*0f5c86ddSBaptiste Daroussin         /* This is the root node, there's no tree to add it to. */
307*0f5c86ddSBaptiste Daroussin         return 1;
308*0f5c86ddSBaptiste Daroussin     }
309*0f5c86ddSBaptiste Daroussin 
310*0f5c86ddSBaptiste Daroussin     parent_index = *((*ctx).top - 1);
311*0f5c86ddSBaptiste Daroussin     parent = &parser->document->nodes.start[parent_index-1];
312*0f5c86ddSBaptiste Daroussin 
313*0f5c86ddSBaptiste Daroussin     switch (parent->type) {
314*0f5c86ddSBaptiste Daroussin         case YAML_SEQUENCE_NODE:
315*0f5c86ddSBaptiste Daroussin             if (!STACK_LIMIT(parser, parent->data.sequence.items, INT_MAX-1))
316*0f5c86ddSBaptiste Daroussin                 return 0;
317*0f5c86ddSBaptiste Daroussin             if (!PUSH(parser, parent->data.sequence.items, index))
318*0f5c86ddSBaptiste Daroussin                 return 0;
319*0f5c86ddSBaptiste Daroussin             break;
320*0f5c86ddSBaptiste Daroussin         case YAML_MAPPING_NODE: {
321*0f5c86ddSBaptiste Daroussin             yaml_node_pair_t pair;
322*0f5c86ddSBaptiste Daroussin             if (!STACK_EMPTY(parser, parent->data.mapping.pairs)) {
323*0f5c86ddSBaptiste Daroussin                 yaml_node_pair_t *p = parent->data.mapping.pairs.top - 1;
324*0f5c86ddSBaptiste Daroussin                 if (p->key != 0 && p->value == 0) {
325*0f5c86ddSBaptiste Daroussin                     p->value = index;
326*0f5c86ddSBaptiste Daroussin                     break;
327*0f5c86ddSBaptiste Daroussin                 }
328*0f5c86ddSBaptiste Daroussin             }
329*0f5c86ddSBaptiste Daroussin 
330*0f5c86ddSBaptiste Daroussin             pair.key = index;
331*0f5c86ddSBaptiste Daroussin             pair.value = 0;
332*0f5c86ddSBaptiste Daroussin             if (!STACK_LIMIT(parser, parent->data.mapping.pairs, INT_MAX-1))
333*0f5c86ddSBaptiste Daroussin                 return 0;
334*0f5c86ddSBaptiste Daroussin             if (!PUSH(parser, parent->data.mapping.pairs, pair))
335*0f5c86ddSBaptiste Daroussin                 return 0;
336*0f5c86ddSBaptiste Daroussin 
337*0f5c86ddSBaptiste Daroussin             break;
338*0f5c86ddSBaptiste Daroussin         }
339*0f5c86ddSBaptiste Daroussin         default:
340*0f5c86ddSBaptiste Daroussin             assert(0); /* Could not happen. */
341*0f5c86ddSBaptiste Daroussin             return 0;
342*0f5c86ddSBaptiste Daroussin     }
343*0f5c86ddSBaptiste Daroussin     return 1;
344*0f5c86ddSBaptiste Daroussin }
345*0f5c86ddSBaptiste Daroussin 
346*0f5c86ddSBaptiste Daroussin /*
347*0f5c86ddSBaptiste Daroussin  * Compose a node corresponding to an alias.
348*0f5c86ddSBaptiste Daroussin  */
349*0f5c86ddSBaptiste Daroussin 
350*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_alias(yaml_parser_t * parser,yaml_event_t * event,struct loader_ctx * ctx)351*0f5c86ddSBaptiste Daroussin yaml_parser_load_alias(yaml_parser_t *parser, yaml_event_t *event,
352*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx)
353*0f5c86ddSBaptiste Daroussin {
354*0f5c86ddSBaptiste Daroussin     yaml_char_t *anchor = event->data.alias.anchor;
355*0f5c86ddSBaptiste Daroussin     yaml_alias_data_t *alias_data;
356*0f5c86ddSBaptiste Daroussin 
357*0f5c86ddSBaptiste Daroussin     for (alias_data = parser->aliases.start;
358*0f5c86ddSBaptiste Daroussin             alias_data != parser->aliases.top; alias_data ++) {
359*0f5c86ddSBaptiste Daroussin         if (strcmp((char *)alias_data->anchor, (char *)anchor) == 0) {
360*0f5c86ddSBaptiste Daroussin             yaml_free(anchor);
361*0f5c86ddSBaptiste Daroussin             return yaml_parser_load_node_add(parser, ctx, alias_data->index);
362*0f5c86ddSBaptiste Daroussin         }
363*0f5c86ddSBaptiste Daroussin     }
364*0f5c86ddSBaptiste Daroussin 
365*0f5c86ddSBaptiste Daroussin     yaml_free(anchor);
366*0f5c86ddSBaptiste Daroussin     return yaml_parser_set_composer_error(parser, "found undefined alias",
367*0f5c86ddSBaptiste Daroussin             event->start_mark);
368*0f5c86ddSBaptiste Daroussin }
369*0f5c86ddSBaptiste Daroussin 
370*0f5c86ddSBaptiste Daroussin /*
371*0f5c86ddSBaptiste Daroussin  * Compose a scalar node.
372*0f5c86ddSBaptiste Daroussin  */
373*0f5c86ddSBaptiste Daroussin 
374*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_scalar(yaml_parser_t * parser,yaml_event_t * event,struct loader_ctx * ctx)375*0f5c86ddSBaptiste Daroussin yaml_parser_load_scalar(yaml_parser_t *parser, yaml_event_t *event,
376*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx)
377*0f5c86ddSBaptiste Daroussin {
378*0f5c86ddSBaptiste Daroussin     yaml_node_t node;
379*0f5c86ddSBaptiste Daroussin     int index;
380*0f5c86ddSBaptiste Daroussin     yaml_char_t *tag = event->data.scalar.tag;
381*0f5c86ddSBaptiste Daroussin 
382*0f5c86ddSBaptiste Daroussin     if (!STACK_LIMIT(parser, parser->document->nodes, INT_MAX-1)) goto error;
383*0f5c86ddSBaptiste Daroussin 
384*0f5c86ddSBaptiste Daroussin     if (!tag || strcmp((char *)tag, "!") == 0) {
385*0f5c86ddSBaptiste Daroussin         yaml_free(tag);
386*0f5c86ddSBaptiste Daroussin         tag = yaml_strdup((yaml_char_t *)YAML_DEFAULT_SCALAR_TAG);
387*0f5c86ddSBaptiste Daroussin         if (!tag) goto error;
388*0f5c86ddSBaptiste Daroussin     }
389*0f5c86ddSBaptiste Daroussin 
390*0f5c86ddSBaptiste Daroussin     SCALAR_NODE_INIT(node, tag, event->data.scalar.value,
391*0f5c86ddSBaptiste Daroussin             event->data.scalar.length, event->data.scalar.style,
392*0f5c86ddSBaptiste Daroussin             event->start_mark, event->end_mark);
393*0f5c86ddSBaptiste Daroussin 
394*0f5c86ddSBaptiste Daroussin     if (!PUSH(parser, parser->document->nodes, node)) goto error;
395*0f5c86ddSBaptiste Daroussin 
396*0f5c86ddSBaptiste Daroussin     index = parser->document->nodes.top - parser->document->nodes.start;
397*0f5c86ddSBaptiste Daroussin 
398*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_register_anchor(parser, index,
399*0f5c86ddSBaptiste Daroussin                 event->data.scalar.anchor)) return 0;
400*0f5c86ddSBaptiste Daroussin 
401*0f5c86ddSBaptiste Daroussin     return yaml_parser_load_node_add(parser, ctx, index);
402*0f5c86ddSBaptiste Daroussin 
403*0f5c86ddSBaptiste Daroussin error:
404*0f5c86ddSBaptiste Daroussin     yaml_free(tag);
405*0f5c86ddSBaptiste Daroussin     yaml_free(event->data.scalar.anchor);
406*0f5c86ddSBaptiste Daroussin     yaml_free(event->data.scalar.value);
407*0f5c86ddSBaptiste Daroussin     return 0;
408*0f5c86ddSBaptiste Daroussin }
409*0f5c86ddSBaptiste Daroussin 
410*0f5c86ddSBaptiste Daroussin /*
411*0f5c86ddSBaptiste Daroussin  * Compose a sequence node.
412*0f5c86ddSBaptiste Daroussin  */
413*0f5c86ddSBaptiste Daroussin 
414*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_sequence(yaml_parser_t * parser,yaml_event_t * event,struct loader_ctx * ctx)415*0f5c86ddSBaptiste Daroussin yaml_parser_load_sequence(yaml_parser_t *parser, yaml_event_t *event,
416*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx)
417*0f5c86ddSBaptiste Daroussin {
418*0f5c86ddSBaptiste Daroussin     yaml_node_t node;
419*0f5c86ddSBaptiste Daroussin     struct {
420*0f5c86ddSBaptiste Daroussin         yaml_node_item_t *start;
421*0f5c86ddSBaptiste Daroussin         yaml_node_item_t *end;
422*0f5c86ddSBaptiste Daroussin         yaml_node_item_t *top;
423*0f5c86ddSBaptiste Daroussin     } items = { NULL, NULL, NULL };
424*0f5c86ddSBaptiste Daroussin     int index;
425*0f5c86ddSBaptiste Daroussin     yaml_char_t *tag = event->data.sequence_start.tag;
426*0f5c86ddSBaptiste Daroussin 
427*0f5c86ddSBaptiste Daroussin     if (!STACK_LIMIT(parser, parser->document->nodes, INT_MAX-1)) goto error;
428*0f5c86ddSBaptiste Daroussin 
429*0f5c86ddSBaptiste Daroussin     if (!tag || strcmp((char *)tag, "!") == 0) {
430*0f5c86ddSBaptiste Daroussin         yaml_free(tag);
431*0f5c86ddSBaptiste Daroussin         tag = yaml_strdup((yaml_char_t *)YAML_DEFAULT_SEQUENCE_TAG);
432*0f5c86ddSBaptiste Daroussin         if (!tag) goto error;
433*0f5c86ddSBaptiste Daroussin     }
434*0f5c86ddSBaptiste Daroussin 
435*0f5c86ddSBaptiste Daroussin     if (!STACK_INIT(parser, items, yaml_node_item_t*)) goto error;
436*0f5c86ddSBaptiste Daroussin 
437*0f5c86ddSBaptiste Daroussin     SEQUENCE_NODE_INIT(node, tag, items.start, items.end,
438*0f5c86ddSBaptiste Daroussin             event->data.sequence_start.style,
439*0f5c86ddSBaptiste Daroussin             event->start_mark, event->end_mark);
440*0f5c86ddSBaptiste Daroussin 
441*0f5c86ddSBaptiste Daroussin     if (!PUSH(parser, parser->document->nodes, node)) goto error;
442*0f5c86ddSBaptiste Daroussin 
443*0f5c86ddSBaptiste Daroussin     index = parser->document->nodes.top - parser->document->nodes.start;
444*0f5c86ddSBaptiste Daroussin 
445*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_register_anchor(parser, index,
446*0f5c86ddSBaptiste Daroussin                 event->data.sequence_start.anchor)) return 0;
447*0f5c86ddSBaptiste Daroussin 
448*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_load_node_add(parser, ctx, index)) return 0;
449*0f5c86ddSBaptiste Daroussin 
450*0f5c86ddSBaptiste Daroussin     if (!STACK_LIMIT(parser, *ctx, INT_MAX-1)) return 0;
451*0f5c86ddSBaptiste Daroussin     if (!PUSH(parser, *ctx, index)) return 0;
452*0f5c86ddSBaptiste Daroussin 
453*0f5c86ddSBaptiste Daroussin     return 1;
454*0f5c86ddSBaptiste Daroussin 
455*0f5c86ddSBaptiste Daroussin error:
456*0f5c86ddSBaptiste Daroussin     yaml_free(tag);
457*0f5c86ddSBaptiste Daroussin     yaml_free(event->data.sequence_start.anchor);
458*0f5c86ddSBaptiste Daroussin     return 0;
459*0f5c86ddSBaptiste Daroussin }
460*0f5c86ddSBaptiste Daroussin 
461*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_sequence_end(yaml_parser_t * parser,yaml_event_t * event,struct loader_ctx * ctx)462*0f5c86ddSBaptiste Daroussin yaml_parser_load_sequence_end(yaml_parser_t *parser, yaml_event_t *event,
463*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx)
464*0f5c86ddSBaptiste Daroussin {
465*0f5c86ddSBaptiste Daroussin     int index;
466*0f5c86ddSBaptiste Daroussin 
467*0f5c86ddSBaptiste Daroussin     assert(((*ctx).top - (*ctx).start) > 0);
468*0f5c86ddSBaptiste Daroussin 
469*0f5c86ddSBaptiste Daroussin     index = *((*ctx).top - 1);
470*0f5c86ddSBaptiste Daroussin     assert(parser->document->nodes.start[index-1].type == YAML_SEQUENCE_NODE);
471*0f5c86ddSBaptiste Daroussin     parser->document->nodes.start[index-1].end_mark = event->end_mark;
472*0f5c86ddSBaptiste Daroussin 
473*0f5c86ddSBaptiste Daroussin     (void)POP(parser, *ctx);
474*0f5c86ddSBaptiste Daroussin 
475*0f5c86ddSBaptiste Daroussin     return 1;
476*0f5c86ddSBaptiste Daroussin }
477*0f5c86ddSBaptiste Daroussin 
478*0f5c86ddSBaptiste Daroussin /*
479*0f5c86ddSBaptiste Daroussin  * Compose a mapping node.
480*0f5c86ddSBaptiste Daroussin  */
481*0f5c86ddSBaptiste Daroussin 
482*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_mapping(yaml_parser_t * parser,yaml_event_t * event,struct loader_ctx * ctx)483*0f5c86ddSBaptiste Daroussin yaml_parser_load_mapping(yaml_parser_t *parser, yaml_event_t *event,
484*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx)
485*0f5c86ddSBaptiste Daroussin {
486*0f5c86ddSBaptiste Daroussin     yaml_node_t node;
487*0f5c86ddSBaptiste Daroussin     struct {
488*0f5c86ddSBaptiste Daroussin         yaml_node_pair_t *start;
489*0f5c86ddSBaptiste Daroussin         yaml_node_pair_t *end;
490*0f5c86ddSBaptiste Daroussin         yaml_node_pair_t *top;
491*0f5c86ddSBaptiste Daroussin     } pairs = { NULL, NULL, NULL };
492*0f5c86ddSBaptiste Daroussin     int index;
493*0f5c86ddSBaptiste Daroussin     yaml_char_t *tag = event->data.mapping_start.tag;
494*0f5c86ddSBaptiste Daroussin 
495*0f5c86ddSBaptiste Daroussin     if (!STACK_LIMIT(parser, parser->document->nodes, INT_MAX-1)) goto error;
496*0f5c86ddSBaptiste Daroussin 
497*0f5c86ddSBaptiste Daroussin     if (!tag || strcmp((char *)tag, "!") == 0) {
498*0f5c86ddSBaptiste Daroussin         yaml_free(tag);
499*0f5c86ddSBaptiste Daroussin         tag = yaml_strdup((yaml_char_t *)YAML_DEFAULT_MAPPING_TAG);
500*0f5c86ddSBaptiste Daroussin         if (!tag) goto error;
501*0f5c86ddSBaptiste Daroussin     }
502*0f5c86ddSBaptiste Daroussin 
503*0f5c86ddSBaptiste Daroussin     if (!STACK_INIT(parser, pairs, yaml_node_pair_t*)) goto error;
504*0f5c86ddSBaptiste Daroussin 
505*0f5c86ddSBaptiste Daroussin     MAPPING_NODE_INIT(node, tag, pairs.start, pairs.end,
506*0f5c86ddSBaptiste Daroussin             event->data.mapping_start.style,
507*0f5c86ddSBaptiste Daroussin             event->start_mark, event->end_mark);
508*0f5c86ddSBaptiste Daroussin 
509*0f5c86ddSBaptiste Daroussin     if (!PUSH(parser, parser->document->nodes, node)) goto error;
510*0f5c86ddSBaptiste Daroussin 
511*0f5c86ddSBaptiste Daroussin     index = parser->document->nodes.top - parser->document->nodes.start;
512*0f5c86ddSBaptiste Daroussin 
513*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_register_anchor(parser, index,
514*0f5c86ddSBaptiste Daroussin                 event->data.mapping_start.anchor)) return 0;
515*0f5c86ddSBaptiste Daroussin 
516*0f5c86ddSBaptiste Daroussin     if (!yaml_parser_load_node_add(parser, ctx, index)) return 0;
517*0f5c86ddSBaptiste Daroussin 
518*0f5c86ddSBaptiste Daroussin     if (!STACK_LIMIT(parser, *ctx, INT_MAX-1)) return 0;
519*0f5c86ddSBaptiste Daroussin     if (!PUSH(parser, *ctx, index)) return 0;
520*0f5c86ddSBaptiste Daroussin 
521*0f5c86ddSBaptiste Daroussin     return 1;
522*0f5c86ddSBaptiste Daroussin 
523*0f5c86ddSBaptiste Daroussin error:
524*0f5c86ddSBaptiste Daroussin     yaml_free(tag);
525*0f5c86ddSBaptiste Daroussin     yaml_free(event->data.mapping_start.anchor);
526*0f5c86ddSBaptiste Daroussin     return 0;
527*0f5c86ddSBaptiste Daroussin }
528*0f5c86ddSBaptiste Daroussin 
529*0f5c86ddSBaptiste Daroussin static int
yaml_parser_load_mapping_end(yaml_parser_t * parser,yaml_event_t * event,struct loader_ctx * ctx)530*0f5c86ddSBaptiste Daroussin yaml_parser_load_mapping_end(yaml_parser_t *parser, yaml_event_t *event,
531*0f5c86ddSBaptiste Daroussin         struct loader_ctx *ctx)
532*0f5c86ddSBaptiste Daroussin {
533*0f5c86ddSBaptiste Daroussin     int index;
534*0f5c86ddSBaptiste Daroussin 
535*0f5c86ddSBaptiste Daroussin     assert(((*ctx).top - (*ctx).start) > 0);
536*0f5c86ddSBaptiste Daroussin 
537*0f5c86ddSBaptiste Daroussin     index = *((*ctx).top - 1);
538*0f5c86ddSBaptiste Daroussin     assert(parser->document->nodes.start[index-1].type == YAML_MAPPING_NODE);
539*0f5c86ddSBaptiste Daroussin     parser->document->nodes.start[index-1].end_mark = event->end_mark;
540*0f5c86ddSBaptiste Daroussin 
541*0f5c86ddSBaptiste Daroussin     (void)POP(parser, *ctx);
542*0f5c86ddSBaptiste Daroussin 
543*0f5c86ddSBaptiste Daroussin     return 1;
544*0f5c86ddSBaptiste Daroussin }