~nskaggs/+junk/xenial-test

« back to all changes in this revision

Viewing changes to src/gopkg.in/yaml.v1/parserc.go

  • Committer: Nicholas Skaggs
  • Date: 2016-10-24 20:56:05 UTC
  • Revision ID: nicholas.skaggs@canonical.com-20161024205605-z8lta0uvuhtxwzwl
Initi with beta15

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
package yaml
 
2
 
 
3
import (
 
4
        "bytes"
 
5
)
 
6
 
 
7
// The parser implements the following grammar:
 
8
//
 
9
// stream               ::= STREAM-START implicit_document? explicit_document* STREAM-END
 
10
// implicit_document    ::= block_node DOCUMENT-END*
 
11
// explicit_document    ::= DIRECTIVE* DOCUMENT-START block_node? DOCUMENT-END*
 
12
// block_node_or_indentless_sequence    ::=
 
13
//                          ALIAS
 
14
//                          | properties (block_content | indentless_block_sequence)?
 
15
//                          | block_content
 
16
//                          | indentless_block_sequence
 
17
// block_node           ::= ALIAS
 
18
//                          | properties block_content?
 
19
//                          | block_content
 
20
// flow_node            ::= ALIAS
 
21
//                          | properties flow_content?
 
22
//                          | flow_content
 
23
// properties           ::= TAG ANCHOR? | ANCHOR TAG?
 
24
// block_content        ::= block_collection | flow_collection | SCALAR
 
25
// flow_content         ::= flow_collection | SCALAR
 
26
// block_collection     ::= block_sequence | block_mapping
 
27
// flow_collection      ::= flow_sequence | flow_mapping
 
28
// block_sequence       ::= BLOCK-SEQUENCE-START (BLOCK-ENTRY block_node?)* BLOCK-END
 
29
// indentless_sequence  ::= (BLOCK-ENTRY block_node?)+
 
30
// block_mapping        ::= BLOCK-MAPPING_START
 
31
//                          ((KEY block_node_or_indentless_sequence?)?
 
32
//                          (VALUE block_node_or_indentless_sequence?)?)*
 
33
//                          BLOCK-END
 
34
// flow_sequence        ::= FLOW-SEQUENCE-START
 
35
//                          (flow_sequence_entry FLOW-ENTRY)*
 
36
//                          flow_sequence_entry?
 
37
//                          FLOW-SEQUENCE-END
 
38
// flow_sequence_entry  ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
39
// flow_mapping         ::= FLOW-MAPPING-START
 
40
//                          (flow_mapping_entry FLOW-ENTRY)*
 
41
//                          flow_mapping_entry?
 
42
//                          FLOW-MAPPING-END
 
43
// flow_mapping_entry   ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
44
 
 
45
// Peek the next token in the token queue.
 
46
func peek_token(parser *yaml_parser_t) *yaml_token_t {
 
47
        if parser.token_available || yaml_parser_fetch_more_tokens(parser) {
 
48
                return &parser.tokens[parser.tokens_head]
 
49
        }
 
50
        return nil
 
51
}
 
52
 
 
53
// Remove the next token from the queue (must be called after peek_token).
 
54
func skip_token(parser *yaml_parser_t) {
 
55
        parser.token_available = false
 
56
        parser.tokens_parsed++
 
57
        parser.stream_end_produced = parser.tokens[parser.tokens_head].typ == yaml_STREAM_END_TOKEN
 
58
        parser.tokens_head++
 
59
}
 
60
 
 
61
// Get the next event.
 
62
func yaml_parser_parse(parser *yaml_parser_t, event *yaml_event_t) bool {
 
63
        // Erase the event object.
 
64
        *event = yaml_event_t{}
 
65
 
 
66
        // No events after the end of the stream or error.
 
67
        if parser.stream_end_produced || parser.error != yaml_NO_ERROR || parser.state == yaml_PARSE_END_STATE {
 
68
                return true
 
69
        }
 
70
 
 
71
        // Generate the next event.
 
72
        return yaml_parser_state_machine(parser, event)
 
73
}
 
74
 
 
75
// Set parser error.
 
76
func yaml_parser_set_parser_error(parser *yaml_parser_t, problem string, problem_mark yaml_mark_t) bool {
 
77
        parser.error = yaml_PARSER_ERROR
 
78
        parser.problem = problem
 
79
        parser.problem_mark = problem_mark
 
80
        return false
 
81
}
 
82
 
 
83
func yaml_parser_set_parser_error_context(parser *yaml_parser_t, context string, context_mark yaml_mark_t, problem string, problem_mark yaml_mark_t) bool {
 
84
        parser.error = yaml_PARSER_ERROR
 
85
        parser.context = context
 
86
        parser.context_mark = context_mark
 
87
        parser.problem = problem
 
88
        parser.problem_mark = problem_mark
 
89
        return false
 
90
}
 
91
 
 
92
// State dispatcher.
 
93
func yaml_parser_state_machine(parser *yaml_parser_t, event *yaml_event_t) bool {
 
94
        //trace("yaml_parser_state_machine", "state:", parser.state.String())
 
95
 
 
96
        switch parser.state {
 
97
        case yaml_PARSE_STREAM_START_STATE:
 
98
                return yaml_parser_parse_stream_start(parser, event)
 
99
 
 
100
        case yaml_PARSE_IMPLICIT_DOCUMENT_START_STATE:
 
101
                return yaml_parser_parse_document_start(parser, event, true)
 
102
 
 
103
        case yaml_PARSE_DOCUMENT_START_STATE:
 
104
                return yaml_parser_parse_document_start(parser, event, false)
 
105
 
 
106
        case yaml_PARSE_DOCUMENT_CONTENT_STATE:
 
107
                return yaml_parser_parse_document_content(parser, event)
 
108
 
 
109
        case yaml_PARSE_DOCUMENT_END_STATE:
 
110
                return yaml_parser_parse_document_end(parser, event)
 
111
 
 
112
        case yaml_PARSE_BLOCK_NODE_STATE:
 
113
                return yaml_parser_parse_node(parser, event, true, false)
 
114
 
 
115
        case yaml_PARSE_BLOCK_NODE_OR_INDENTLESS_SEQUENCE_STATE:
 
116
                return yaml_parser_parse_node(parser, event, true, true)
 
117
 
 
118
        case yaml_PARSE_FLOW_NODE_STATE:
 
119
                return yaml_parser_parse_node(parser, event, false, false)
 
120
 
 
121
        case yaml_PARSE_BLOCK_SEQUENCE_FIRST_ENTRY_STATE:
 
122
                return yaml_parser_parse_block_sequence_entry(parser, event, true)
 
123
 
 
124
        case yaml_PARSE_BLOCK_SEQUENCE_ENTRY_STATE:
 
125
                return yaml_parser_parse_block_sequence_entry(parser, event, false)
 
126
 
 
127
        case yaml_PARSE_INDENTLESS_SEQUENCE_ENTRY_STATE:
 
128
                return yaml_parser_parse_indentless_sequence_entry(parser, event)
 
129
 
 
130
        case yaml_PARSE_BLOCK_MAPPING_FIRST_KEY_STATE:
 
131
                return yaml_parser_parse_block_mapping_key(parser, event, true)
 
132
 
 
133
        case yaml_PARSE_BLOCK_MAPPING_KEY_STATE:
 
134
                return yaml_parser_parse_block_mapping_key(parser, event, false)
 
135
 
 
136
        case yaml_PARSE_BLOCK_MAPPING_VALUE_STATE:
 
137
                return yaml_parser_parse_block_mapping_value(parser, event)
 
138
 
 
139
        case yaml_PARSE_FLOW_SEQUENCE_FIRST_ENTRY_STATE:
 
140
                return yaml_parser_parse_flow_sequence_entry(parser, event, true)
 
141
 
 
142
        case yaml_PARSE_FLOW_SEQUENCE_ENTRY_STATE:
 
143
                return yaml_parser_parse_flow_sequence_entry(parser, event, false)
 
144
 
 
145
        case yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_KEY_STATE:
 
146
                return yaml_parser_parse_flow_sequence_entry_mapping_key(parser, event)
 
147
 
 
148
        case yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_VALUE_STATE:
 
149
                return yaml_parser_parse_flow_sequence_entry_mapping_value(parser, event)
 
150
 
 
151
        case yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_END_STATE:
 
152
                return yaml_parser_parse_flow_sequence_entry_mapping_end(parser, event)
 
153
 
 
154
        case yaml_PARSE_FLOW_MAPPING_FIRST_KEY_STATE:
 
155
                return yaml_parser_parse_flow_mapping_key(parser, event, true)
 
156
 
 
157
        case yaml_PARSE_FLOW_MAPPING_KEY_STATE:
 
158
                return yaml_parser_parse_flow_mapping_key(parser, event, false)
 
159
 
 
160
        case yaml_PARSE_FLOW_MAPPING_VALUE_STATE:
 
161
                return yaml_parser_parse_flow_mapping_value(parser, event, false)
 
162
 
 
163
        case yaml_PARSE_FLOW_MAPPING_EMPTY_VALUE_STATE:
 
164
                return yaml_parser_parse_flow_mapping_value(parser, event, true)
 
165
 
 
166
        default:
 
167
                panic("invalid parser state")
 
168
        }
 
169
        return false
 
170
}
 
171
 
 
172
// Parse the production:
 
173
// stream   ::= STREAM-START implicit_document? explicit_document* STREAM-END
 
174
//              ************
 
175
func yaml_parser_parse_stream_start(parser *yaml_parser_t, event *yaml_event_t) bool {
 
176
        token := peek_token(parser)
 
177
        if token == nil {
 
178
                return false
 
179
        }
 
180
        if token.typ != yaml_STREAM_START_TOKEN {
 
181
                return yaml_parser_set_parser_error(parser, "did not find expected <stream-start>", token.start_mark)
 
182
        }
 
183
        parser.state = yaml_PARSE_IMPLICIT_DOCUMENT_START_STATE
 
184
        *event = yaml_event_t{
 
185
                typ:        yaml_STREAM_START_EVENT,
 
186
                start_mark: token.start_mark,
 
187
                end_mark:   token.end_mark,
 
188
                encoding:   token.encoding,
 
189
        }
 
190
        skip_token(parser)
 
191
        return true
 
192
}
 
193
 
 
194
// Parse the productions:
 
195
// implicit_document    ::= block_node DOCUMENT-END*
 
196
//                          *
 
197
// explicit_document    ::= DIRECTIVE* DOCUMENT-START block_node? DOCUMENT-END*
 
198
//                          *************************
 
199
func yaml_parser_parse_document_start(parser *yaml_parser_t, event *yaml_event_t, implicit bool) bool {
 
200
 
 
201
        token := peek_token(parser)
 
202
        if token == nil {
 
203
                return false
 
204
        }
 
205
 
 
206
        // Parse extra document end indicators.
 
207
        if !implicit {
 
208
                for token.typ == yaml_DOCUMENT_END_TOKEN {
 
209
                        skip_token(parser)
 
210
                        token = peek_token(parser)
 
211
                        if token == nil {
 
212
                                return false
 
213
                        }
 
214
                }
 
215
        }
 
216
 
 
217
        if implicit && token.typ != yaml_VERSION_DIRECTIVE_TOKEN &&
 
218
                token.typ != yaml_TAG_DIRECTIVE_TOKEN &&
 
219
                token.typ != yaml_DOCUMENT_START_TOKEN &&
 
220
                token.typ != yaml_STREAM_END_TOKEN {
 
221
                // Parse an implicit document.
 
222
                if !yaml_parser_process_directives(parser, nil, nil) {
 
223
                        return false
 
224
                }
 
225
                parser.states = append(parser.states, yaml_PARSE_DOCUMENT_END_STATE)
 
226
                parser.state = yaml_PARSE_BLOCK_NODE_STATE
 
227
 
 
228
                *event = yaml_event_t{
 
229
                        typ:        yaml_DOCUMENT_START_EVENT,
 
230
                        start_mark: token.start_mark,
 
231
                        end_mark:   token.end_mark,
 
232
                }
 
233
 
 
234
        } else if token.typ != yaml_STREAM_END_TOKEN {
 
235
                // Parse an explicit document.
 
236
                var version_directive *yaml_version_directive_t
 
237
                var tag_directives []yaml_tag_directive_t
 
238
                start_mark := token.start_mark
 
239
                if !yaml_parser_process_directives(parser, &version_directive, &tag_directives) {
 
240
                        return false
 
241
                }
 
242
                token = peek_token(parser)
 
243
                if token == nil {
 
244
                        return false
 
245
                }
 
246
                if token.typ != yaml_DOCUMENT_START_TOKEN {
 
247
                        yaml_parser_set_parser_error(parser,
 
248
                                "did not find expected <document start>", token.start_mark)
 
249
                        return false
 
250
                }
 
251
                parser.states = append(parser.states, yaml_PARSE_DOCUMENT_END_STATE)
 
252
                parser.state = yaml_PARSE_DOCUMENT_CONTENT_STATE
 
253
                end_mark := token.end_mark
 
254
 
 
255
                *event = yaml_event_t{
 
256
                        typ:               yaml_DOCUMENT_START_EVENT,
 
257
                        start_mark:        start_mark,
 
258
                        end_mark:          end_mark,
 
259
                        version_directive: version_directive,
 
260
                        tag_directives:    tag_directives,
 
261
                        implicit:          false,
 
262
                }
 
263
                skip_token(parser)
 
264
 
 
265
        } else {
 
266
                // Parse the stream end.
 
267
                parser.state = yaml_PARSE_END_STATE
 
268
                *event = yaml_event_t{
 
269
                        typ:        yaml_STREAM_END_EVENT,
 
270
                        start_mark: token.start_mark,
 
271
                        end_mark:   token.end_mark,
 
272
                }
 
273
                skip_token(parser)
 
274
        }
 
275
 
 
276
        return true
 
277
}
 
278
 
 
279
// Parse the productions:
 
280
// explicit_document    ::= DIRECTIVE* DOCUMENT-START block_node? DOCUMENT-END*
 
281
//                                                    ***********
 
282
//
 
283
func yaml_parser_parse_document_content(parser *yaml_parser_t, event *yaml_event_t) bool {
 
284
        token := peek_token(parser)
 
285
        if token == nil {
 
286
                return false
 
287
        }
 
288
        if token.typ == yaml_VERSION_DIRECTIVE_TOKEN ||
 
289
                token.typ == yaml_TAG_DIRECTIVE_TOKEN ||
 
290
                token.typ == yaml_DOCUMENT_START_TOKEN ||
 
291
                token.typ == yaml_DOCUMENT_END_TOKEN ||
 
292
                token.typ == yaml_STREAM_END_TOKEN {
 
293
                parser.state = parser.states[len(parser.states)-1]
 
294
                parser.states = parser.states[:len(parser.states)-1]
 
295
                return yaml_parser_process_empty_scalar(parser, event,
 
296
                        token.start_mark)
 
297
        }
 
298
        return yaml_parser_parse_node(parser, event, true, false)
 
299
}
 
300
 
 
301
// Parse the productions:
 
302
// implicit_document    ::= block_node DOCUMENT-END*
 
303
//                                     *************
 
304
// explicit_document    ::= DIRECTIVE* DOCUMENT-START block_node? DOCUMENT-END*
 
305
//
 
306
func yaml_parser_parse_document_end(parser *yaml_parser_t, event *yaml_event_t) bool {
 
307
        token := peek_token(parser)
 
308
        if token == nil {
 
309
                return false
 
310
        }
 
311
 
 
312
        start_mark := token.start_mark
 
313
        end_mark := token.start_mark
 
314
 
 
315
        implicit := true
 
316
        if token.typ == yaml_DOCUMENT_END_TOKEN {
 
317
                end_mark = token.end_mark
 
318
                skip_token(parser)
 
319
                implicit = false
 
320
        }
 
321
 
 
322
        parser.tag_directives = parser.tag_directives[:0]
 
323
 
 
324
        parser.state = yaml_PARSE_DOCUMENT_START_STATE
 
325
        *event = yaml_event_t{
 
326
                typ:        yaml_DOCUMENT_END_EVENT,
 
327
                start_mark: start_mark,
 
328
                end_mark:   end_mark,
 
329
                implicit:   implicit,
 
330
        }
 
331
        return true
 
332
}
 
333
 
 
334
// Parse the productions:
 
335
// block_node_or_indentless_sequence    ::=
 
336
//                          ALIAS
 
337
//                          *****
 
338
//                          | properties (block_content | indentless_block_sequence)?
 
339
//                            **********  *
 
340
//                          | block_content | indentless_block_sequence
 
341
//                            *
 
342
// block_node           ::= ALIAS
 
343
//                          *****
 
344
//                          | properties block_content?
 
345
//                            ********** *
 
346
//                          | block_content
 
347
//                            *
 
348
// flow_node            ::= ALIAS
 
349
//                          *****
 
350
//                          | properties flow_content?
 
351
//                            ********** *
 
352
//                          | flow_content
 
353
//                            *
 
354
// properties           ::= TAG ANCHOR? | ANCHOR TAG?
 
355
//                          *************************
 
356
// block_content        ::= block_collection | flow_collection | SCALAR
 
357
//                                                               ******
 
358
// flow_content         ::= flow_collection | SCALAR
 
359
//                                            ******
 
360
func yaml_parser_parse_node(parser *yaml_parser_t, event *yaml_event_t, block, indentless_sequence bool) bool {
 
361
        //defer trace("yaml_parser_parse_node", "block:", block, "indentless_sequence:", indentless_sequence)()
 
362
 
 
363
        token := peek_token(parser)
 
364
        if token == nil {
 
365
                return false
 
366
        }
 
367
 
 
368
        if token.typ == yaml_ALIAS_TOKEN {
 
369
                parser.state = parser.states[len(parser.states)-1]
 
370
                parser.states = parser.states[:len(parser.states)-1]
 
371
                *event = yaml_event_t{
 
372
                        typ:        yaml_ALIAS_EVENT,
 
373
                        start_mark: token.start_mark,
 
374
                        end_mark:   token.end_mark,
 
375
                        anchor:     token.value,
 
376
                }
 
377
                skip_token(parser)
 
378
                return true
 
379
        }
 
380
 
 
381
        start_mark := token.start_mark
 
382
        end_mark := token.start_mark
 
383
 
 
384
        var tag_token bool
 
385
        var tag_handle, tag_suffix, anchor []byte
 
386
        var tag_mark yaml_mark_t
 
387
        if token.typ == yaml_ANCHOR_TOKEN {
 
388
                anchor = token.value
 
389
                start_mark = token.start_mark
 
390
                end_mark = token.end_mark
 
391
                skip_token(parser)
 
392
                token = peek_token(parser)
 
393
                if token == nil {
 
394
                        return false
 
395
                }
 
396
                if token.typ == yaml_TAG_TOKEN {
 
397
                        tag_token = true
 
398
                        tag_handle = token.value
 
399
                        tag_suffix = token.suffix
 
400
                        tag_mark = token.start_mark
 
401
                        end_mark = token.end_mark
 
402
                        skip_token(parser)
 
403
                        token = peek_token(parser)
 
404
                        if token == nil {
 
405
                                return false
 
406
                        }
 
407
                }
 
408
        } else if token.typ == yaml_TAG_TOKEN {
 
409
                tag_token = true
 
410
                tag_handle = token.value
 
411
                tag_suffix = token.suffix
 
412
                start_mark = token.start_mark
 
413
                tag_mark = token.start_mark
 
414
                end_mark = token.end_mark
 
415
                skip_token(parser)
 
416
                token = peek_token(parser)
 
417
                if token == nil {
 
418
                        return false
 
419
                }
 
420
                if token.typ == yaml_ANCHOR_TOKEN {
 
421
                        anchor = token.value
 
422
                        end_mark = token.end_mark
 
423
                        skip_token(parser)
 
424
                        token = peek_token(parser)
 
425
                        if token == nil {
 
426
                                return false
 
427
                        }
 
428
                }
 
429
        }
 
430
 
 
431
        var tag []byte
 
432
        if tag_token {
 
433
                if len(tag_handle) == 0 {
 
434
                        tag = tag_suffix
 
435
                        tag_suffix = nil
 
436
                } else {
 
437
                        for i := range parser.tag_directives {
 
438
                                if bytes.Equal(parser.tag_directives[i].handle, tag_handle) {
 
439
                                        tag = append([]byte(nil), parser.tag_directives[i].prefix...)
 
440
                                        tag = append(tag, tag_suffix...)
 
441
                                        break
 
442
                                }
 
443
                        }
 
444
                        if len(tag) == 0 {
 
445
                                yaml_parser_set_parser_error_context(parser,
 
446
                                        "while parsing a node", start_mark,
 
447
                                        "found undefined tag handle", tag_mark)
 
448
                                return false
 
449
                        }
 
450
                }
 
451
        }
 
452
 
 
453
        implicit := len(tag) == 0
 
454
        if indentless_sequence && token.typ == yaml_BLOCK_ENTRY_TOKEN {
 
455
                end_mark = token.end_mark
 
456
                parser.state = yaml_PARSE_INDENTLESS_SEQUENCE_ENTRY_STATE
 
457
                *event = yaml_event_t{
 
458
                        typ:        yaml_SEQUENCE_START_EVENT,
 
459
                        start_mark: start_mark,
 
460
                        end_mark:   end_mark,
 
461
                        anchor:     anchor,
 
462
                        tag:        tag,
 
463
                        implicit:   implicit,
 
464
                        style:      yaml_style_t(yaml_BLOCK_SEQUENCE_STYLE),
 
465
                }
 
466
                return true
 
467
        }
 
468
        if token.typ == yaml_SCALAR_TOKEN {
 
469
                var plain_implicit, quoted_implicit bool
 
470
                end_mark = token.end_mark
 
471
                if (len(tag) == 0 && token.style == yaml_PLAIN_SCALAR_STYLE) || (len(tag) == 1 && tag[0] == '!') {
 
472
                        plain_implicit = true
 
473
                } else if len(tag) == 0 {
 
474
                        quoted_implicit = true
 
475
                }
 
476
                parser.state = parser.states[len(parser.states)-1]
 
477
                parser.states = parser.states[:len(parser.states)-1]
 
478
 
 
479
                *event = yaml_event_t{
 
480
                        typ:             yaml_SCALAR_EVENT,
 
481
                        start_mark:      start_mark,
 
482
                        end_mark:        end_mark,
 
483
                        anchor:          anchor,
 
484
                        tag:             tag,
 
485
                        value:           token.value,
 
486
                        implicit:        plain_implicit,
 
487
                        quoted_implicit: quoted_implicit,
 
488
                        style:           yaml_style_t(token.style),
 
489
                }
 
490
                skip_token(parser)
 
491
                return true
 
492
        }
 
493
        if token.typ == yaml_FLOW_SEQUENCE_START_TOKEN {
 
494
                // [Go] Some of the events below can be merged as they differ only on style.
 
495
                end_mark = token.end_mark
 
496
                parser.state = yaml_PARSE_FLOW_SEQUENCE_FIRST_ENTRY_STATE
 
497
                *event = yaml_event_t{
 
498
                        typ:        yaml_SEQUENCE_START_EVENT,
 
499
                        start_mark: start_mark,
 
500
                        end_mark:   end_mark,
 
501
                        anchor:     anchor,
 
502
                        tag:        tag,
 
503
                        implicit:   implicit,
 
504
                        style:      yaml_style_t(yaml_FLOW_SEQUENCE_STYLE),
 
505
                }
 
506
                return true
 
507
        }
 
508
        if token.typ == yaml_FLOW_MAPPING_START_TOKEN {
 
509
                end_mark = token.end_mark
 
510
                parser.state = yaml_PARSE_FLOW_MAPPING_FIRST_KEY_STATE
 
511
                *event = yaml_event_t{
 
512
                        typ:        yaml_MAPPING_START_EVENT,
 
513
                        start_mark: start_mark,
 
514
                        end_mark:   end_mark,
 
515
                        anchor:     anchor,
 
516
                        tag:        tag,
 
517
                        implicit:   implicit,
 
518
                        style:      yaml_style_t(yaml_FLOW_MAPPING_STYLE),
 
519
                }
 
520
                return true
 
521
        }
 
522
        if block && token.typ == yaml_BLOCK_SEQUENCE_START_TOKEN {
 
523
                end_mark = token.end_mark
 
524
                parser.state = yaml_PARSE_BLOCK_SEQUENCE_FIRST_ENTRY_STATE
 
525
                *event = yaml_event_t{
 
526
                        typ:        yaml_SEQUENCE_START_EVENT,
 
527
                        start_mark: start_mark,
 
528
                        end_mark:   end_mark,
 
529
                        anchor:     anchor,
 
530
                        tag:        tag,
 
531
                        implicit:   implicit,
 
532
                        style:      yaml_style_t(yaml_BLOCK_SEQUENCE_STYLE),
 
533
                }
 
534
                return true
 
535
        }
 
536
        if block && token.typ == yaml_BLOCK_MAPPING_START_TOKEN {
 
537
                end_mark = token.end_mark
 
538
                parser.state = yaml_PARSE_BLOCK_MAPPING_FIRST_KEY_STATE
 
539
                *event = yaml_event_t{
 
540
                        typ:        yaml_MAPPING_START_EVENT,
 
541
                        start_mark: start_mark,
 
542
                        end_mark:   end_mark,
 
543
                        anchor:     anchor,
 
544
                        tag:        tag,
 
545
                        implicit:   implicit,
 
546
                        style:      yaml_style_t(yaml_BLOCK_MAPPING_STYLE),
 
547
                }
 
548
                return true
 
549
        }
 
550
        if len(anchor) > 0 || len(tag) > 0 {
 
551
                parser.state = parser.states[len(parser.states)-1]
 
552
                parser.states = parser.states[:len(parser.states)-1]
 
553
 
 
554
                *event = yaml_event_t{
 
555
                        typ:             yaml_SCALAR_EVENT,
 
556
                        start_mark:      start_mark,
 
557
                        end_mark:        end_mark,
 
558
                        anchor:          anchor,
 
559
                        tag:             tag,
 
560
                        implicit:        implicit,
 
561
                        quoted_implicit: false,
 
562
                        style:           yaml_style_t(yaml_PLAIN_SCALAR_STYLE),
 
563
                }
 
564
                return true
 
565
        }
 
566
 
 
567
        context := "while parsing a flow node"
 
568
        if block {
 
569
                context = "while parsing a block node"
 
570
        }
 
571
        yaml_parser_set_parser_error_context(parser, context, start_mark,
 
572
                "did not find expected node content", token.start_mark)
 
573
        return false
 
574
}
 
575
 
 
576
// Parse the productions:
 
577
// block_sequence ::= BLOCK-SEQUENCE-START (BLOCK-ENTRY block_node?)* BLOCK-END
 
578
//                    ********************  *********** *             *********
 
579
//
 
580
func yaml_parser_parse_block_sequence_entry(parser *yaml_parser_t, event *yaml_event_t, first bool) bool {
 
581
        if first {
 
582
                token := peek_token(parser)
 
583
                parser.marks = append(parser.marks, token.start_mark)
 
584
                skip_token(parser)
 
585
        }
 
586
 
 
587
        token := peek_token(parser)
 
588
        if token == nil {
 
589
                return false
 
590
        }
 
591
 
 
592
        if token.typ == yaml_BLOCK_ENTRY_TOKEN {
 
593
                mark := token.end_mark
 
594
                skip_token(parser)
 
595
                token = peek_token(parser)
 
596
                if token == nil {
 
597
                        return false
 
598
                }
 
599
                if token.typ != yaml_BLOCK_ENTRY_TOKEN && token.typ != yaml_BLOCK_END_TOKEN {
 
600
                        parser.states = append(parser.states, yaml_PARSE_BLOCK_SEQUENCE_ENTRY_STATE)
 
601
                        return yaml_parser_parse_node(parser, event, true, false)
 
602
                } else {
 
603
                        parser.state = yaml_PARSE_BLOCK_SEQUENCE_ENTRY_STATE
 
604
                        return yaml_parser_process_empty_scalar(parser, event, mark)
 
605
                }
 
606
        }
 
607
        if token.typ == yaml_BLOCK_END_TOKEN {
 
608
                parser.state = parser.states[len(parser.states)-1]
 
609
                parser.states = parser.states[:len(parser.states)-1]
 
610
                parser.marks = parser.marks[:len(parser.marks)-1]
 
611
 
 
612
                *event = yaml_event_t{
 
613
                        typ:        yaml_SEQUENCE_END_EVENT,
 
614
                        start_mark: token.start_mark,
 
615
                        end_mark:   token.end_mark,
 
616
                }
 
617
 
 
618
                skip_token(parser)
 
619
                return true
 
620
        }
 
621
 
 
622
        context_mark := parser.marks[len(parser.marks)-1]
 
623
        parser.marks = parser.marks[:len(parser.marks)-1]
 
624
        return yaml_parser_set_parser_error_context(parser,
 
625
                "while parsing a block collection", context_mark,
 
626
                "did not find expected '-' indicator", token.start_mark)
 
627
}
 
628
 
 
629
// Parse the productions:
 
630
// indentless_sequence  ::= (BLOCK-ENTRY block_node?)+
 
631
//                           *********** *
 
632
func yaml_parser_parse_indentless_sequence_entry(parser *yaml_parser_t, event *yaml_event_t) bool {
 
633
        token := peek_token(parser)
 
634
        if token == nil {
 
635
                return false
 
636
        }
 
637
 
 
638
        if token.typ == yaml_BLOCK_ENTRY_TOKEN {
 
639
                mark := token.end_mark
 
640
                skip_token(parser)
 
641
                token = peek_token(parser)
 
642
                if token == nil {
 
643
                        return false
 
644
                }
 
645
                if token.typ != yaml_BLOCK_ENTRY_TOKEN &&
 
646
                        token.typ != yaml_KEY_TOKEN &&
 
647
                        token.typ != yaml_VALUE_TOKEN &&
 
648
                        token.typ != yaml_BLOCK_END_TOKEN {
 
649
                        parser.states = append(parser.states, yaml_PARSE_INDENTLESS_SEQUENCE_ENTRY_STATE)
 
650
                        return yaml_parser_parse_node(parser, event, true, false)
 
651
                }
 
652
                parser.state = yaml_PARSE_INDENTLESS_SEQUENCE_ENTRY_STATE
 
653
                return yaml_parser_process_empty_scalar(parser, event, mark)
 
654
        }
 
655
        parser.state = parser.states[len(parser.states)-1]
 
656
        parser.states = parser.states[:len(parser.states)-1]
 
657
 
 
658
        *event = yaml_event_t{
 
659
                typ:        yaml_SEQUENCE_END_EVENT,
 
660
                start_mark: token.start_mark,
 
661
                end_mark:   token.start_mark, // [Go] Shouldn't this be token.end_mark?
 
662
        }
 
663
        return true
 
664
}
 
665
 
 
666
// Parse the productions:
 
667
// block_mapping        ::= BLOCK-MAPPING_START
 
668
//                          *******************
 
669
//                          ((KEY block_node_or_indentless_sequence?)?
 
670
//                            *** *
 
671
//                          (VALUE block_node_or_indentless_sequence?)?)*
 
672
//
 
673
//                          BLOCK-END
 
674
//                          *********
 
675
//
 
676
func yaml_parser_parse_block_mapping_key(parser *yaml_parser_t, event *yaml_event_t, first bool) bool {
 
677
        if first {
 
678
                token := peek_token(parser)
 
679
                parser.marks = append(parser.marks, token.start_mark)
 
680
                skip_token(parser)
 
681
        }
 
682
 
 
683
        token := peek_token(parser)
 
684
        if token == nil {
 
685
                return false
 
686
        }
 
687
 
 
688
        if token.typ == yaml_KEY_TOKEN {
 
689
                mark := token.end_mark
 
690
                skip_token(parser)
 
691
                token = peek_token(parser)
 
692
                if token == nil {
 
693
                        return false
 
694
                }
 
695
                if token.typ != yaml_KEY_TOKEN &&
 
696
                        token.typ != yaml_VALUE_TOKEN &&
 
697
                        token.typ != yaml_BLOCK_END_TOKEN {
 
698
                        parser.states = append(parser.states, yaml_PARSE_BLOCK_MAPPING_VALUE_STATE)
 
699
                        return yaml_parser_parse_node(parser, event, true, true)
 
700
                } else {
 
701
                        parser.state = yaml_PARSE_BLOCK_MAPPING_VALUE_STATE
 
702
                        return yaml_parser_process_empty_scalar(parser, event, mark)
 
703
                }
 
704
        } else if token.typ == yaml_BLOCK_END_TOKEN {
 
705
                parser.state = parser.states[len(parser.states)-1]
 
706
                parser.states = parser.states[:len(parser.states)-1]
 
707
                parser.marks = parser.marks[:len(parser.marks)-1]
 
708
                *event = yaml_event_t{
 
709
                        typ:        yaml_MAPPING_END_EVENT,
 
710
                        start_mark: token.start_mark,
 
711
                        end_mark:   token.end_mark,
 
712
                }
 
713
                skip_token(parser)
 
714
                return true
 
715
        }
 
716
 
 
717
        context_mark := parser.marks[len(parser.marks)-1]
 
718
        parser.marks = parser.marks[:len(parser.marks)-1]
 
719
        return yaml_parser_set_parser_error_context(parser,
 
720
                "while parsing a block mapping", context_mark,
 
721
                "did not find expected key", token.start_mark)
 
722
}
 
723
 
 
724
// Parse the productions:
 
725
// block_mapping        ::= BLOCK-MAPPING_START
 
726
//
 
727
//                          ((KEY block_node_or_indentless_sequence?)?
 
728
//
 
729
//                          (VALUE block_node_or_indentless_sequence?)?)*
 
730
//                           ***** *
 
731
//                          BLOCK-END
 
732
//
 
733
//
 
734
func yaml_parser_parse_block_mapping_value(parser *yaml_parser_t, event *yaml_event_t) bool {
 
735
        token := peek_token(parser)
 
736
        if token == nil {
 
737
                return false
 
738
        }
 
739
        if token.typ == yaml_VALUE_TOKEN {
 
740
                mark := token.end_mark
 
741
                skip_token(parser)
 
742
                token = peek_token(parser)
 
743
                if token == nil {
 
744
                        return false
 
745
                }
 
746
                if token.typ != yaml_KEY_TOKEN &&
 
747
                        token.typ != yaml_VALUE_TOKEN &&
 
748
                        token.typ != yaml_BLOCK_END_TOKEN {
 
749
                        parser.states = append(parser.states, yaml_PARSE_BLOCK_MAPPING_KEY_STATE)
 
750
                        return yaml_parser_parse_node(parser, event, true, true)
 
751
                }
 
752
                parser.state = yaml_PARSE_BLOCK_MAPPING_KEY_STATE
 
753
                return yaml_parser_process_empty_scalar(parser, event, mark)
 
754
        }
 
755
        parser.state = yaml_PARSE_BLOCK_MAPPING_KEY_STATE
 
756
        return yaml_parser_process_empty_scalar(parser, event, token.start_mark)
 
757
}
 
758
 
 
759
// Parse the productions:
 
760
// flow_sequence        ::= FLOW-SEQUENCE-START
 
761
//                          *******************
 
762
//                          (flow_sequence_entry FLOW-ENTRY)*
 
763
//                           *                   **********
 
764
//                          flow_sequence_entry?
 
765
//                          *
 
766
//                          FLOW-SEQUENCE-END
 
767
//                          *****************
 
768
// flow_sequence_entry  ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
769
//                          *
 
770
//
 
771
func yaml_parser_parse_flow_sequence_entry(parser *yaml_parser_t, event *yaml_event_t, first bool) bool {
 
772
        if first {
 
773
                token := peek_token(parser)
 
774
                parser.marks = append(parser.marks, token.start_mark)
 
775
                skip_token(parser)
 
776
        }
 
777
        token := peek_token(parser)
 
778
        if token == nil {
 
779
                return false
 
780
        }
 
781
        if token.typ != yaml_FLOW_SEQUENCE_END_TOKEN {
 
782
                if !first {
 
783
                        if token.typ == yaml_FLOW_ENTRY_TOKEN {
 
784
                                skip_token(parser)
 
785
                                token = peek_token(parser)
 
786
                                if token == nil {
 
787
                                        return false
 
788
                                }
 
789
                        } else {
 
790
                                context_mark := parser.marks[len(parser.marks)-1]
 
791
                                parser.marks = parser.marks[:len(parser.marks)-1]
 
792
                                return yaml_parser_set_parser_error_context(parser,
 
793
                                        "while parsing a flow sequence", context_mark,
 
794
                                        "did not find expected ',' or ']'", token.start_mark)
 
795
                        }
 
796
                }
 
797
 
 
798
                if token.typ == yaml_KEY_TOKEN {
 
799
                        parser.state = yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_KEY_STATE
 
800
                        *event = yaml_event_t{
 
801
                                typ:        yaml_MAPPING_START_EVENT,
 
802
                                start_mark: token.start_mark,
 
803
                                end_mark:   token.end_mark,
 
804
                                implicit:   true,
 
805
                                style:      yaml_style_t(yaml_FLOW_MAPPING_STYLE),
 
806
                        }
 
807
                        skip_token(parser)
 
808
                        return true
 
809
                } else if token.typ != yaml_FLOW_SEQUENCE_END_TOKEN {
 
810
                        parser.states = append(parser.states, yaml_PARSE_FLOW_SEQUENCE_ENTRY_STATE)
 
811
                        return yaml_parser_parse_node(parser, event, false, false)
 
812
                }
 
813
        }
 
814
 
 
815
        parser.state = parser.states[len(parser.states)-1]
 
816
        parser.states = parser.states[:len(parser.states)-1]
 
817
        parser.marks = parser.marks[:len(parser.marks)-1]
 
818
 
 
819
        *event = yaml_event_t{
 
820
                typ:        yaml_SEQUENCE_END_EVENT,
 
821
                start_mark: token.start_mark,
 
822
                end_mark:   token.end_mark,
 
823
        }
 
824
 
 
825
        skip_token(parser)
 
826
        return true
 
827
}
 
828
 
 
829
//
 
830
// Parse the productions:
 
831
// flow_sequence_entry  ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
832
//                                      *** *
 
833
//
 
834
func yaml_parser_parse_flow_sequence_entry_mapping_key(parser *yaml_parser_t, event *yaml_event_t) bool {
 
835
        token := peek_token(parser)
 
836
        if token == nil {
 
837
                return false
 
838
        }
 
839
        if token.typ != yaml_VALUE_TOKEN &&
 
840
                token.typ != yaml_FLOW_ENTRY_TOKEN &&
 
841
                token.typ != yaml_FLOW_SEQUENCE_END_TOKEN {
 
842
                parser.states = append(parser.states, yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_VALUE_STATE)
 
843
                return yaml_parser_parse_node(parser, event, false, false)
 
844
        }
 
845
        mark := token.end_mark
 
846
        skip_token(parser)
 
847
        parser.state = yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_VALUE_STATE
 
848
        return yaml_parser_process_empty_scalar(parser, event, mark)
 
849
}
 
850
 
 
851
// Parse the productions:
 
852
// flow_sequence_entry  ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
853
//                                                      ***** *
 
854
//
 
855
func yaml_parser_parse_flow_sequence_entry_mapping_value(parser *yaml_parser_t, event *yaml_event_t) bool {
 
856
        token := peek_token(parser)
 
857
        if token == nil {
 
858
                return false
 
859
        }
 
860
        if token.typ == yaml_VALUE_TOKEN {
 
861
                skip_token(parser)
 
862
                token := peek_token(parser)
 
863
                if token == nil {
 
864
                        return false
 
865
                }
 
866
                if token.typ != yaml_FLOW_ENTRY_TOKEN && token.typ != yaml_FLOW_SEQUENCE_END_TOKEN {
 
867
                        parser.states = append(parser.states, yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_END_STATE)
 
868
                        return yaml_parser_parse_node(parser, event, false, false)
 
869
                }
 
870
        }
 
871
        parser.state = yaml_PARSE_FLOW_SEQUENCE_ENTRY_MAPPING_END_STATE
 
872
        return yaml_parser_process_empty_scalar(parser, event, token.start_mark)
 
873
}
 
874
 
 
875
// Parse the productions:
 
876
// flow_sequence_entry  ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
877
//                                                                      *
 
878
//
 
879
func yaml_parser_parse_flow_sequence_entry_mapping_end(parser *yaml_parser_t, event *yaml_event_t) bool {
 
880
        token := peek_token(parser)
 
881
        if token == nil {
 
882
                return false
 
883
        }
 
884
        parser.state = yaml_PARSE_FLOW_SEQUENCE_ENTRY_STATE
 
885
        *event = yaml_event_t{
 
886
                typ:        yaml_MAPPING_END_EVENT,
 
887
                start_mark: token.start_mark,
 
888
                end_mark:   token.start_mark, // [Go] Shouldn't this be end_mark?
 
889
        }
 
890
        return true
 
891
}
 
892
 
 
893
// Parse the productions:
 
894
// flow_mapping         ::= FLOW-MAPPING-START
 
895
//                          ******************
 
896
//                          (flow_mapping_entry FLOW-ENTRY)*
 
897
//                           *                  **********
 
898
//                          flow_mapping_entry?
 
899
//                          ******************
 
900
//                          FLOW-MAPPING-END
 
901
//                          ****************
 
902
// flow_mapping_entry   ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
903
//                          *           *** *
 
904
//
 
905
func yaml_parser_parse_flow_mapping_key(parser *yaml_parser_t, event *yaml_event_t, first bool) bool {
 
906
        if first {
 
907
                token := peek_token(parser)
 
908
                parser.marks = append(parser.marks, token.start_mark)
 
909
                skip_token(parser)
 
910
        }
 
911
 
 
912
        token := peek_token(parser)
 
913
        if token == nil {
 
914
                return false
 
915
        }
 
916
 
 
917
        if token.typ != yaml_FLOW_MAPPING_END_TOKEN {
 
918
                if !first {
 
919
                        if token.typ == yaml_FLOW_ENTRY_TOKEN {
 
920
                                skip_token(parser)
 
921
                                token = peek_token(parser)
 
922
                                if token == nil {
 
923
                                        return false
 
924
                                }
 
925
                        } else {
 
926
                                context_mark := parser.marks[len(parser.marks)-1]
 
927
                                parser.marks = parser.marks[:len(parser.marks)-1]
 
928
                                return yaml_parser_set_parser_error_context(parser,
 
929
                                        "while parsing a flow mapping", context_mark,
 
930
                                        "did not find expected ',' or '}'", token.start_mark)
 
931
                        }
 
932
                }
 
933
 
 
934
                if token.typ == yaml_KEY_TOKEN {
 
935
                        skip_token(parser)
 
936
                        token = peek_token(parser)
 
937
                        if token == nil {
 
938
                                return false
 
939
                        }
 
940
                        if token.typ != yaml_VALUE_TOKEN &&
 
941
                                token.typ != yaml_FLOW_ENTRY_TOKEN &&
 
942
                                token.typ != yaml_FLOW_MAPPING_END_TOKEN {
 
943
                                parser.states = append(parser.states, yaml_PARSE_FLOW_MAPPING_VALUE_STATE)
 
944
                                return yaml_parser_parse_node(parser, event, false, false)
 
945
                        } else {
 
946
                                parser.state = yaml_PARSE_FLOW_MAPPING_VALUE_STATE
 
947
                                return yaml_parser_process_empty_scalar(parser, event, token.start_mark)
 
948
                        }
 
949
                } else if token.typ != yaml_FLOW_MAPPING_END_TOKEN {
 
950
                        parser.states = append(parser.states, yaml_PARSE_FLOW_MAPPING_EMPTY_VALUE_STATE)
 
951
                        return yaml_parser_parse_node(parser, event, false, false)
 
952
                }
 
953
        }
 
954
 
 
955
        parser.state = parser.states[len(parser.states)-1]
 
956
        parser.states = parser.states[:len(parser.states)-1]
 
957
        parser.marks = parser.marks[:len(parser.marks)-1]
 
958
        *event = yaml_event_t{
 
959
                typ:        yaml_MAPPING_END_EVENT,
 
960
                start_mark: token.start_mark,
 
961
                end_mark:   token.end_mark,
 
962
        }
 
963
        skip_token(parser)
 
964
        return true
 
965
}
 
966
 
 
967
// Parse the productions:
 
968
// flow_mapping_entry   ::= flow_node | KEY flow_node? (VALUE flow_node?)?
 
969
//                                   *                  ***** *
 
970
//
 
971
func yaml_parser_parse_flow_mapping_value(parser *yaml_parser_t, event *yaml_event_t, empty bool) bool {
 
972
        token := peek_token(parser)
 
973
        if token == nil {
 
974
                return false
 
975
        }
 
976
        if empty {
 
977
                parser.state = yaml_PARSE_FLOW_MAPPING_KEY_STATE
 
978
                return yaml_parser_process_empty_scalar(parser, event, token.start_mark)
 
979
        }
 
980
        if token.typ == yaml_VALUE_TOKEN {
 
981
                skip_token(parser)
 
982
                token = peek_token(parser)
 
983
                if token == nil {
 
984
                        return false
 
985
                }
 
986
                if token.typ != yaml_FLOW_ENTRY_TOKEN && token.typ != yaml_FLOW_MAPPING_END_TOKEN {
 
987
                        parser.states = append(parser.states, yaml_PARSE_FLOW_MAPPING_KEY_STATE)
 
988
                        return yaml_parser_parse_node(parser, event, false, false)
 
989
                }
 
990
        }
 
991
        parser.state = yaml_PARSE_FLOW_MAPPING_KEY_STATE
 
992
        return yaml_parser_process_empty_scalar(parser, event, token.start_mark)
 
993
}
 
994
 
 
995
// Generate an empty scalar event.
 
996
func yaml_parser_process_empty_scalar(parser *yaml_parser_t, event *yaml_event_t, mark yaml_mark_t) bool {
 
997
        *event = yaml_event_t{
 
998
                typ:        yaml_SCALAR_EVENT,
 
999
                start_mark: mark,
 
1000
                end_mark:   mark,
 
1001
                value:      nil, // Empty
 
1002
                implicit:   true,
 
1003
                style:      yaml_style_t(yaml_PLAIN_SCALAR_STYLE),
 
1004
        }
 
1005
        return true
 
1006
}
 
1007
 
 
1008
var default_tag_directives = []yaml_tag_directive_t{
 
1009
        {[]byte("!"), []byte("!")},
 
1010
        {[]byte("!!"), []byte("tag:yaml.org,2002:")},
 
1011
}
 
1012
 
 
1013
// Parse directives.
 
1014
func yaml_parser_process_directives(parser *yaml_parser_t,
 
1015
        version_directive_ref **yaml_version_directive_t,
 
1016
        tag_directives_ref *[]yaml_tag_directive_t) bool {
 
1017
 
 
1018
        var version_directive *yaml_version_directive_t
 
1019
        var tag_directives []yaml_tag_directive_t
 
1020
 
 
1021
        token := peek_token(parser)
 
1022
        if token == nil {
 
1023
                return false
 
1024
        }
 
1025
 
 
1026
        for token.typ == yaml_VERSION_DIRECTIVE_TOKEN || token.typ == yaml_TAG_DIRECTIVE_TOKEN {
 
1027
                if token.typ == yaml_VERSION_DIRECTIVE_TOKEN {
 
1028
                        if version_directive != nil {
 
1029
                                yaml_parser_set_parser_error(parser,
 
1030
                                        "found duplicate %YAML directive", token.start_mark)
 
1031
                                return false
 
1032
                        }
 
1033
                        if token.major != 1 || token.minor != 1 {
 
1034
                                yaml_parser_set_parser_error(parser,
 
1035
                                        "found incompatible YAML document", token.start_mark)
 
1036
                                return false
 
1037
                        }
 
1038
                        version_directive = &yaml_version_directive_t{
 
1039
                                major: token.major,
 
1040
                                minor: token.minor,
 
1041
                        }
 
1042
                } else if token.typ == yaml_TAG_DIRECTIVE_TOKEN {
 
1043
                        value := yaml_tag_directive_t{
 
1044
                                handle: token.value,
 
1045
                                prefix: token.prefix,
 
1046
                        }
 
1047
                        if !yaml_parser_append_tag_directive(parser, value, false, token.start_mark) {
 
1048
                                return false
 
1049
                        }
 
1050
                        tag_directives = append(tag_directives, value)
 
1051
                }
 
1052
 
 
1053
                skip_token(parser)
 
1054
                token = peek_token(parser)
 
1055
                if token == nil {
 
1056
                        return false
 
1057
                }
 
1058
        }
 
1059
 
 
1060
        for i := range default_tag_directives {
 
1061
                if !yaml_parser_append_tag_directive(parser, default_tag_directives[i], true, token.start_mark) {
 
1062
                        return false
 
1063
                }
 
1064
        }
 
1065
 
 
1066
        if version_directive_ref != nil {
 
1067
                *version_directive_ref = version_directive
 
1068
        }
 
1069
        if tag_directives_ref != nil {
 
1070
                *tag_directives_ref = tag_directives
 
1071
        }
 
1072
        return true
 
1073
}
 
1074
 
 
1075
// Append a tag directive to the directives stack.
 
1076
func yaml_parser_append_tag_directive(parser *yaml_parser_t, value yaml_tag_directive_t, allow_duplicates bool, mark yaml_mark_t) bool {
 
1077
        for i := range parser.tag_directives {
 
1078
                if bytes.Equal(value.handle, parser.tag_directives[i].handle) {
 
1079
                        if allow_duplicates {
 
1080
                                return true
 
1081
                        }
 
1082
                        return yaml_parser_set_parser_error(parser, "found duplicate %TAG directive", mark)
 
1083
                }
 
1084
        }
 
1085
 
 
1086
        // [Go] I suspect the copy is unnecessary. This was likely done
 
1087
        // because there was no way to track ownership of the data.
 
1088
        value_copy := yaml_tag_directive_t{
 
1089
                handle: make([]byte, len(value.handle)),
 
1090
                prefix: make([]byte, len(value.prefix)),
 
1091
        }
 
1092
        copy(value_copy.handle, value.handle)
 
1093
        copy(value_copy.prefix, value.prefix)
 
1094
        parser.tag_directives = append(parser.tag_directives, value_copy)
 
1095
        return true
 
1096
}