blob: 65846e6749796bcd8c9d1ea275e66e827aadc917 [file] [log] [blame]
mpagenkoaf801632020-07-03 10:00:42 +00001//
2// Copyright (c) 2011-2019 Canonical Ltd
3// Copyright (c) 2006-2010 Kirill Simonov
4//
5// Permission is hereby granted, free of charge, to any person obtaining a copy of
6// this software and associated documentation files (the "Software"), to deal in
7// the Software without restriction, including without limitation the rights to
8// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
9// of the Software, and to permit persons to whom the Software is furnished to do
10// so, subject to the following conditions:
11//
12// The above copyright notice and this permission notice shall be included in all
13// copies or substantial portions of the Software.
14//
15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21// SOFTWARE.
22
Holger Hildebrandtda7758b2020-03-16 11:30:03 +000023package yaml
24
25import (
26 "io"
27)
28
29func yaml_insert_token(parser *yaml_parser_t, pos int, token *yaml_token_t) {
30 //fmt.Println("yaml_insert_token", "pos:", pos, "typ:", token.typ, "head:", parser.tokens_head, "len:", len(parser.tokens))
31
32 // Check if we can move the queue at the beginning of the buffer.
33 if parser.tokens_head > 0 && len(parser.tokens) == cap(parser.tokens) {
34 if parser.tokens_head != len(parser.tokens) {
35 copy(parser.tokens, parser.tokens[parser.tokens_head:])
36 }
37 parser.tokens = parser.tokens[:len(parser.tokens)-parser.tokens_head]
38 parser.tokens_head = 0
39 }
40 parser.tokens = append(parser.tokens, *token)
41 if pos < 0 {
42 return
43 }
44 copy(parser.tokens[parser.tokens_head+pos+1:], parser.tokens[parser.tokens_head+pos:])
45 parser.tokens[parser.tokens_head+pos] = *token
46}
47
48// Create a new parser object.
49func yaml_parser_initialize(parser *yaml_parser_t) bool {
50 *parser = yaml_parser_t{
51 raw_buffer: make([]byte, 0, input_raw_buffer_size),
52 buffer: make([]byte, 0, input_buffer_size),
53 }
54 return true
55}
56
57// Destroy a parser object.
58func yaml_parser_delete(parser *yaml_parser_t) {
59 *parser = yaml_parser_t{}
60}
61
62// String read handler.
63func yaml_string_read_handler(parser *yaml_parser_t, buffer []byte) (n int, err error) {
64 if parser.input_pos == len(parser.input) {
65 return 0, io.EOF
66 }
67 n = copy(buffer, parser.input[parser.input_pos:])
68 parser.input_pos += n
69 return n, nil
70}
71
72// Reader read handler.
73func yaml_reader_read_handler(parser *yaml_parser_t, buffer []byte) (n int, err error) {
74 return parser.input_reader.Read(buffer)
75}
76
77// Set a string input.
78func yaml_parser_set_input_string(parser *yaml_parser_t, input []byte) {
79 if parser.read_handler != nil {
80 panic("must set the input source only once")
81 }
82 parser.read_handler = yaml_string_read_handler
83 parser.input = input
84 parser.input_pos = 0
85}
86
87// Set a file input.
88func yaml_parser_set_input_reader(parser *yaml_parser_t, r io.Reader) {
89 if parser.read_handler != nil {
90 panic("must set the input source only once")
91 }
92 parser.read_handler = yaml_reader_read_handler
93 parser.input_reader = r
94}
95
96// Set the source encoding.
97func yaml_parser_set_encoding(parser *yaml_parser_t, encoding yaml_encoding_t) {
98 if parser.encoding != yaml_ANY_ENCODING {
99 panic("must set the encoding only once")
100 }
101 parser.encoding = encoding
102}
103
104// Create a new emitter object.
105func yaml_emitter_initialize(emitter *yaml_emitter_t) {
106 *emitter = yaml_emitter_t{
107 buffer: make([]byte, output_buffer_size),
108 raw_buffer: make([]byte, 0, output_raw_buffer_size),
109 states: make([]yaml_emitter_state_t, 0, initial_stack_size),
110 events: make([]yaml_event_t, 0, initial_queue_size),
111 }
112}
113
114// Destroy an emitter object.
115func yaml_emitter_delete(emitter *yaml_emitter_t) {
116 *emitter = yaml_emitter_t{}
117}
118
119// String write handler.
120func yaml_string_write_handler(emitter *yaml_emitter_t, buffer []byte) error {
121 *emitter.output_buffer = append(*emitter.output_buffer, buffer...)
122 return nil
123}
124
125// yaml_writer_write_handler uses emitter.output_writer to write the
126// emitted text.
127func yaml_writer_write_handler(emitter *yaml_emitter_t, buffer []byte) error {
128 _, err := emitter.output_writer.Write(buffer)
129 return err
130}
131
132// Set a string output.
133func yaml_emitter_set_output_string(emitter *yaml_emitter_t, output_buffer *[]byte) {
134 if emitter.write_handler != nil {
135 panic("must set the output target only once")
136 }
137 emitter.write_handler = yaml_string_write_handler
138 emitter.output_buffer = output_buffer
139}
140
141// Set a file output.
142func yaml_emitter_set_output_writer(emitter *yaml_emitter_t, w io.Writer) {
143 if emitter.write_handler != nil {
144 panic("must set the output target only once")
145 }
146 emitter.write_handler = yaml_writer_write_handler
147 emitter.output_writer = w
148}
149
150// Set the output encoding.
151func yaml_emitter_set_encoding(emitter *yaml_emitter_t, encoding yaml_encoding_t) {
152 if emitter.encoding != yaml_ANY_ENCODING {
153 panic("must set the output encoding only once")
154 }
155 emitter.encoding = encoding
156}
157
158// Set the canonical output style.
159func yaml_emitter_set_canonical(emitter *yaml_emitter_t, canonical bool) {
160 emitter.canonical = canonical
161}
162
mpagenkoaf801632020-07-03 10:00:42 +0000163// Set the indentation increment.
Holger Hildebrandtda7758b2020-03-16 11:30:03 +0000164func yaml_emitter_set_indent(emitter *yaml_emitter_t, indent int) {
165 if indent < 2 || indent > 9 {
166 indent = 2
167 }
168 emitter.best_indent = indent
169}
170
171// Set the preferred line width.
172func yaml_emitter_set_width(emitter *yaml_emitter_t, width int) {
173 if width < 0 {
174 width = -1
175 }
176 emitter.best_width = width
177}
178
179// Set if unescaped non-ASCII characters are allowed.
180func yaml_emitter_set_unicode(emitter *yaml_emitter_t, unicode bool) {
181 emitter.unicode = unicode
182}
183
184// Set the preferred line break character.
185func yaml_emitter_set_break(emitter *yaml_emitter_t, line_break yaml_break_t) {
186 emitter.line_break = line_break
187}
188
189///*
190// * Destroy a token object.
191// */
192//
193//YAML_DECLARE(void)
194//yaml_token_delete(yaml_token_t *token)
195//{
196// assert(token); // Non-NULL token object expected.
197//
198// switch (token.type)
199// {
200// case YAML_TAG_DIRECTIVE_TOKEN:
201// yaml_free(token.data.tag_directive.handle);
202// yaml_free(token.data.tag_directive.prefix);
203// break;
204//
205// case YAML_ALIAS_TOKEN:
206// yaml_free(token.data.alias.value);
207// break;
208//
209// case YAML_ANCHOR_TOKEN:
210// yaml_free(token.data.anchor.value);
211// break;
212//
213// case YAML_TAG_TOKEN:
214// yaml_free(token.data.tag.handle);
215// yaml_free(token.data.tag.suffix);
216// break;
217//
218// case YAML_SCALAR_TOKEN:
219// yaml_free(token.data.scalar.value);
220// break;
221//
222// default:
223// break;
224// }
225//
226// memset(token, 0, sizeof(yaml_token_t));
227//}
228//
229///*
230// * Check if a string is a valid UTF-8 sequence.
231// *
232// * Check 'reader.c' for more details on UTF-8 encoding.
233// */
234//
235//static int
236//yaml_check_utf8(yaml_char_t *start, size_t length)
237//{
238// yaml_char_t *end = start+length;
239// yaml_char_t *pointer = start;
240//
241// while (pointer < end) {
242// unsigned char octet;
243// unsigned int width;
244// unsigned int value;
245// size_t k;
246//
247// octet = pointer[0];
248// width = (octet & 0x80) == 0x00 ? 1 :
249// (octet & 0xE0) == 0xC0 ? 2 :
250// (octet & 0xF0) == 0xE0 ? 3 :
251// (octet & 0xF8) == 0xF0 ? 4 : 0;
252// value = (octet & 0x80) == 0x00 ? octet & 0x7F :
253// (octet & 0xE0) == 0xC0 ? octet & 0x1F :
254// (octet & 0xF0) == 0xE0 ? octet & 0x0F :
255// (octet & 0xF8) == 0xF0 ? octet & 0x07 : 0;
256// if (!width) return 0;
257// if (pointer+width > end) return 0;
258// for (k = 1; k < width; k ++) {
259// octet = pointer[k];
260// if ((octet & 0xC0) != 0x80) return 0;
261// value = (value << 6) + (octet & 0x3F);
262// }
263// if (!((width == 1) ||
264// (width == 2 && value >= 0x80) ||
265// (width == 3 && value >= 0x800) ||
266// (width == 4 && value >= 0x10000))) return 0;
267//
268// pointer += width;
269// }
270//
271// return 1;
272//}
273//
274
275// Create STREAM-START.
276func yaml_stream_start_event_initialize(event *yaml_event_t, encoding yaml_encoding_t) {
277 *event = yaml_event_t{
278 typ: yaml_STREAM_START_EVENT,
279 encoding: encoding,
280 }
281}
282
283// Create STREAM-END.
284func yaml_stream_end_event_initialize(event *yaml_event_t) {
285 *event = yaml_event_t{
286 typ: yaml_STREAM_END_EVENT,
287 }
288}
289
290// Create DOCUMENT-START.
291func yaml_document_start_event_initialize(
292 event *yaml_event_t,
293 version_directive *yaml_version_directive_t,
294 tag_directives []yaml_tag_directive_t,
295 implicit bool,
296) {
297 *event = yaml_event_t{
298 typ: yaml_DOCUMENT_START_EVENT,
299 version_directive: version_directive,
300 tag_directives: tag_directives,
301 implicit: implicit,
302 }
303}
304
305// Create DOCUMENT-END.
306func yaml_document_end_event_initialize(event *yaml_event_t, implicit bool) {
307 *event = yaml_event_t{
308 typ: yaml_DOCUMENT_END_EVENT,
309 implicit: implicit,
310 }
311}
312
mpagenkoaf801632020-07-03 10:00:42 +0000313// Create ALIAS.
314func yaml_alias_event_initialize(event *yaml_event_t, anchor []byte) bool {
315 *event = yaml_event_t{
316 typ: yaml_ALIAS_EVENT,
317 anchor: anchor,
318 }
319 return true
320}
Holger Hildebrandtda7758b2020-03-16 11:30:03 +0000321
322// Create SCALAR.
323func yaml_scalar_event_initialize(event *yaml_event_t, anchor, tag, value []byte, plain_implicit, quoted_implicit bool, style yaml_scalar_style_t) bool {
324 *event = yaml_event_t{
325 typ: yaml_SCALAR_EVENT,
326 anchor: anchor,
327 tag: tag,
328 value: value,
329 implicit: plain_implicit,
330 quoted_implicit: quoted_implicit,
331 style: yaml_style_t(style),
332 }
333 return true
334}
335
336// Create SEQUENCE-START.
337func yaml_sequence_start_event_initialize(event *yaml_event_t, anchor, tag []byte, implicit bool, style yaml_sequence_style_t) bool {
338 *event = yaml_event_t{
339 typ: yaml_SEQUENCE_START_EVENT,
340 anchor: anchor,
341 tag: tag,
342 implicit: implicit,
343 style: yaml_style_t(style),
344 }
345 return true
346}
347
348// Create SEQUENCE-END.
349func yaml_sequence_end_event_initialize(event *yaml_event_t) bool {
350 *event = yaml_event_t{
351 typ: yaml_SEQUENCE_END_EVENT,
352 }
353 return true
354}
355
356// Create MAPPING-START.
357func yaml_mapping_start_event_initialize(event *yaml_event_t, anchor, tag []byte, implicit bool, style yaml_mapping_style_t) {
358 *event = yaml_event_t{
359 typ: yaml_MAPPING_START_EVENT,
360 anchor: anchor,
361 tag: tag,
362 implicit: implicit,
363 style: yaml_style_t(style),
364 }
365}
366
367// Create MAPPING-END.
368func yaml_mapping_end_event_initialize(event *yaml_event_t) {
369 *event = yaml_event_t{
370 typ: yaml_MAPPING_END_EVENT,
371 }
372}
373
374// Destroy an event object.
375func yaml_event_delete(event *yaml_event_t) {
376 *event = yaml_event_t{}
377}
378
379///*
380// * Create a document object.
381// */
382//
383//YAML_DECLARE(int)
384//yaml_document_initialize(document *yaml_document_t,
385// version_directive *yaml_version_directive_t,
386// tag_directives_start *yaml_tag_directive_t,
387// tag_directives_end *yaml_tag_directive_t,
388// start_implicit int, end_implicit int)
389//{
390// struct {
391// error yaml_error_type_t
392// } context
393// struct {
394// start *yaml_node_t
395// end *yaml_node_t
396// top *yaml_node_t
397// } nodes = { NULL, NULL, NULL }
398// version_directive_copy *yaml_version_directive_t = NULL
399// struct {
400// start *yaml_tag_directive_t
401// end *yaml_tag_directive_t
402// top *yaml_tag_directive_t
403// } tag_directives_copy = { NULL, NULL, NULL }
404// value yaml_tag_directive_t = { NULL, NULL }
405// mark yaml_mark_t = { 0, 0, 0 }
406//
407// assert(document) // Non-NULL document object is expected.
408// assert((tag_directives_start && tag_directives_end) ||
409// (tag_directives_start == tag_directives_end))
410// // Valid tag directives are expected.
411//
412// if (!STACK_INIT(&context, nodes, INITIAL_STACK_SIZE)) goto error
413//
414// if (version_directive) {
415// version_directive_copy = yaml_malloc(sizeof(yaml_version_directive_t))
416// if (!version_directive_copy) goto error
417// version_directive_copy.major = version_directive.major
418// version_directive_copy.minor = version_directive.minor
419// }
420//
421// if (tag_directives_start != tag_directives_end) {
422// tag_directive *yaml_tag_directive_t
423// if (!STACK_INIT(&context, tag_directives_copy, INITIAL_STACK_SIZE))
424// goto error
425// for (tag_directive = tag_directives_start
426// tag_directive != tag_directives_end; tag_directive ++) {
427// assert(tag_directive.handle)
428// assert(tag_directive.prefix)
429// if (!yaml_check_utf8(tag_directive.handle,
430// strlen((char *)tag_directive.handle)))
431// goto error
432// if (!yaml_check_utf8(tag_directive.prefix,
433// strlen((char *)tag_directive.prefix)))
434// goto error
435// value.handle = yaml_strdup(tag_directive.handle)
436// value.prefix = yaml_strdup(tag_directive.prefix)
437// if (!value.handle || !value.prefix) goto error
438// if (!PUSH(&context, tag_directives_copy, value))
439// goto error
440// value.handle = NULL
441// value.prefix = NULL
442// }
443// }
444//
445// DOCUMENT_INIT(*document, nodes.start, nodes.end, version_directive_copy,
446// tag_directives_copy.start, tag_directives_copy.top,
447// start_implicit, end_implicit, mark, mark)
448//
449// return 1
450//
451//error:
452// STACK_DEL(&context, nodes)
453// yaml_free(version_directive_copy)
454// while (!STACK_EMPTY(&context, tag_directives_copy)) {
455// value yaml_tag_directive_t = POP(&context, tag_directives_copy)
456// yaml_free(value.handle)
457// yaml_free(value.prefix)
458// }
459// STACK_DEL(&context, tag_directives_copy)
460// yaml_free(value.handle)
461// yaml_free(value.prefix)
462//
463// return 0
464//}
465//
466///*
467// * Destroy a document object.
468// */
469//
470//YAML_DECLARE(void)
471//yaml_document_delete(document *yaml_document_t)
472//{
473// struct {
474// error yaml_error_type_t
475// } context
476// tag_directive *yaml_tag_directive_t
477//
478// context.error = YAML_NO_ERROR // Eliminate a compiler warning.
479//
480// assert(document) // Non-NULL document object is expected.
481//
482// while (!STACK_EMPTY(&context, document.nodes)) {
483// node yaml_node_t = POP(&context, document.nodes)
484// yaml_free(node.tag)
485// switch (node.type) {
486// case YAML_SCALAR_NODE:
487// yaml_free(node.data.scalar.value)
488// break
489// case YAML_SEQUENCE_NODE:
490// STACK_DEL(&context, node.data.sequence.items)
491// break
492// case YAML_MAPPING_NODE:
493// STACK_DEL(&context, node.data.mapping.pairs)
494// break
495// default:
496// assert(0) // Should not happen.
497// }
498// }
499// STACK_DEL(&context, document.nodes)
500//
501// yaml_free(document.version_directive)
502// for (tag_directive = document.tag_directives.start
503// tag_directive != document.tag_directives.end
504// tag_directive++) {
505// yaml_free(tag_directive.handle)
506// yaml_free(tag_directive.prefix)
507// }
508// yaml_free(document.tag_directives.start)
509//
510// memset(document, 0, sizeof(yaml_document_t))
511//}
512//
513///**
514// * Get a document node.
515// */
516//
517//YAML_DECLARE(yaml_node_t *)
518//yaml_document_get_node(document *yaml_document_t, index int)
519//{
520// assert(document) // Non-NULL document object is expected.
521//
522// if (index > 0 && document.nodes.start + index <= document.nodes.top) {
523// return document.nodes.start + index - 1
524// }
525// return NULL
526//}
527//
528///**
529// * Get the root object.
530// */
531//
532//YAML_DECLARE(yaml_node_t *)
533//yaml_document_get_root_node(document *yaml_document_t)
534//{
535// assert(document) // Non-NULL document object is expected.
536//
537// if (document.nodes.top != document.nodes.start) {
538// return document.nodes.start
539// }
540// return NULL
541//}
542//
543///*
544// * Add a scalar node to a document.
545// */
546//
547//YAML_DECLARE(int)
548//yaml_document_add_scalar(document *yaml_document_t,
549// tag *yaml_char_t, value *yaml_char_t, length int,
550// style yaml_scalar_style_t)
551//{
552// struct {
553// error yaml_error_type_t
554// } context
555// mark yaml_mark_t = { 0, 0, 0 }
556// tag_copy *yaml_char_t = NULL
557// value_copy *yaml_char_t = NULL
558// node yaml_node_t
559//
560// assert(document) // Non-NULL document object is expected.
561// assert(value) // Non-NULL value is expected.
562//
563// if (!tag) {
564// tag = (yaml_char_t *)YAML_DEFAULT_SCALAR_TAG
565// }
566//
567// if (!yaml_check_utf8(tag, strlen((char *)tag))) goto error
568// tag_copy = yaml_strdup(tag)
569// if (!tag_copy) goto error
570//
571// if (length < 0) {
572// length = strlen((char *)value)
573// }
574//
575// if (!yaml_check_utf8(value, length)) goto error
576// value_copy = yaml_malloc(length+1)
577// if (!value_copy) goto error
578// memcpy(value_copy, value, length)
579// value_copy[length] = '\0'
580//
581// SCALAR_NODE_INIT(node, tag_copy, value_copy, length, style, mark, mark)
582// if (!PUSH(&context, document.nodes, node)) goto error
583//
584// return document.nodes.top - document.nodes.start
585//
586//error:
587// yaml_free(tag_copy)
588// yaml_free(value_copy)
589//
590// return 0
591//}
592//
593///*
594// * Add a sequence node to a document.
595// */
596//
597//YAML_DECLARE(int)
598//yaml_document_add_sequence(document *yaml_document_t,
599// tag *yaml_char_t, style yaml_sequence_style_t)
600//{
601// struct {
602// error yaml_error_type_t
603// } context
604// mark yaml_mark_t = { 0, 0, 0 }
605// tag_copy *yaml_char_t = NULL
606// struct {
607// start *yaml_node_item_t
608// end *yaml_node_item_t
609// top *yaml_node_item_t
610// } items = { NULL, NULL, NULL }
611// node yaml_node_t
612//
613// assert(document) // Non-NULL document object is expected.
614//
615// if (!tag) {
616// tag = (yaml_char_t *)YAML_DEFAULT_SEQUENCE_TAG
617// }
618//
619// if (!yaml_check_utf8(tag, strlen((char *)tag))) goto error
620// tag_copy = yaml_strdup(tag)
621// if (!tag_copy) goto error
622//
623// if (!STACK_INIT(&context, items, INITIAL_STACK_SIZE)) goto error
624//
625// SEQUENCE_NODE_INIT(node, tag_copy, items.start, items.end,
626// style, mark, mark)
627// if (!PUSH(&context, document.nodes, node)) goto error
628//
629// return document.nodes.top - document.nodes.start
630//
631//error:
632// STACK_DEL(&context, items)
633// yaml_free(tag_copy)
634//
635// return 0
636//}
637//
638///*
639// * Add a mapping node to a document.
640// */
641//
642//YAML_DECLARE(int)
643//yaml_document_add_mapping(document *yaml_document_t,
644// tag *yaml_char_t, style yaml_mapping_style_t)
645//{
646// struct {
647// error yaml_error_type_t
648// } context
649// mark yaml_mark_t = { 0, 0, 0 }
650// tag_copy *yaml_char_t = NULL
651// struct {
652// start *yaml_node_pair_t
653// end *yaml_node_pair_t
654// top *yaml_node_pair_t
655// } pairs = { NULL, NULL, NULL }
656// node yaml_node_t
657//
658// assert(document) // Non-NULL document object is expected.
659//
660// if (!tag) {
661// tag = (yaml_char_t *)YAML_DEFAULT_MAPPING_TAG
662// }
663//
664// if (!yaml_check_utf8(tag, strlen((char *)tag))) goto error
665// tag_copy = yaml_strdup(tag)
666// if (!tag_copy) goto error
667//
668// if (!STACK_INIT(&context, pairs, INITIAL_STACK_SIZE)) goto error
669//
670// MAPPING_NODE_INIT(node, tag_copy, pairs.start, pairs.end,
671// style, mark, mark)
672// if (!PUSH(&context, document.nodes, node)) goto error
673//
674// return document.nodes.top - document.nodes.start
675//
676//error:
677// STACK_DEL(&context, pairs)
678// yaml_free(tag_copy)
679//
680// return 0
681//}
682//
683///*
684// * Append an item to a sequence node.
685// */
686//
687//YAML_DECLARE(int)
688//yaml_document_append_sequence_item(document *yaml_document_t,
689// sequence int, item int)
690//{
691// struct {
692// error yaml_error_type_t
693// } context
694//
695// assert(document) // Non-NULL document is required.
696// assert(sequence > 0
697// && document.nodes.start + sequence <= document.nodes.top)
698// // Valid sequence id is required.
699// assert(document.nodes.start[sequence-1].type == YAML_SEQUENCE_NODE)
700// // A sequence node is required.
701// assert(item > 0 && document.nodes.start + item <= document.nodes.top)
702// // Valid item id is required.
703//
704// if (!PUSH(&context,
705// document.nodes.start[sequence-1].data.sequence.items, item))
706// return 0
707//
708// return 1
709//}
710//
711///*
712// * Append a pair of a key and a value to a mapping node.
713// */
714//
715//YAML_DECLARE(int)
716//yaml_document_append_mapping_pair(document *yaml_document_t,
717// mapping int, key int, value int)
718//{
719// struct {
720// error yaml_error_type_t
721// } context
722//
723// pair yaml_node_pair_t
724//
725// assert(document) // Non-NULL document is required.
726// assert(mapping > 0
727// && document.nodes.start + mapping <= document.nodes.top)
728// // Valid mapping id is required.
729// assert(document.nodes.start[mapping-1].type == YAML_MAPPING_NODE)
730// // A mapping node is required.
731// assert(key > 0 && document.nodes.start + key <= document.nodes.top)
732// // Valid key id is required.
733// assert(value > 0 && document.nodes.start + value <= document.nodes.top)
734// // Valid value id is required.
735//
736// pair.key = key
737// pair.value = value
738//
739// if (!PUSH(&context,
740// document.nodes.start[mapping-1].data.mapping.pairs, pair))
741// return 0
742//
743// return 1
744//}
745//
746//