33 return malloc(size ? size : 1);
43 return ptr ? realloc(ptr, size ? size : 1) : malloc(size ? size : 1);
79 if (!new_start)
return 0;
81 memset(new_start + (*end - *start), 0, *end - *start);
83 *pointer = new_start + (*pointer - *start);
84 *end = new_start + (*end - *start)*2;
100 if (*b_start == *b_pointer)
103 while (*a_end - *a_pointer <= *b_pointer - *b_start) {
108 memcpy(*a_pointer, *b_start, *b_pointer - *b_start);
109 *a_pointer += *b_pointer - *b_start;
123 if ((
char *)*end - (
char *)*start >= INT_MAX / 2)
126 new_start =
yaml_realloc(*start, ((
char *)*end - (
char *)*start)*2);
128 if (!new_start)
return 0;
130 *top = (
char *)new_start + ((
char *)*top - (
char *)*start);
131 *end = (
char *)new_start + ((
char *)*end - (
char *)*start)*2;
146 if (*start == *head && *tail == *end) {
148 ((
char *)*end - (
char *)*start)*2);
150 if (!new_start)
return 0;
152 *head = (
char *)new_start + ((
char *)*head - (
char *)*start);
153 *tail = (
char *)new_start + ((
char *)*tail - (
char *)*start);
154 *end = (
char *)new_start + ((
char *)*end - (
char *)*start)*2;
161 if (*head != *tail) {
162 memmove(*start, *head, (
char *)*tail - (
char *)*head);
164 *tail = (
char *)*tail - (
char *)*head + (
char *)*start;
188 if (!
STACK_INIT(parser, parser->indents,
int*))
210 STACK_DEL(parser, parser->tag_directives);
234 while (!
STACK_EMPTY(parser, parser->tag_directives)) {
239 STACK_DEL(parser, parser->tag_directives);
249 yaml_string_read_handler(
void *
data,
unsigned char *buffer,
size_t size,
264 memcpy(buffer, parser->
input.
string.current, size);
275 yaml_file_read_handler(
void *
data,
unsigned char *buffer,
size_t size,
280 *size_read = fread(buffer, 1, size, parser->
input.
file);
290 const
unsigned char *input,
size_t size)
293 assert(!parser->read_handler);
296 parser->read_handler = yaml_string_read_handler;
297 parser->read_handler_data = parser;
299 parser->input.string.start = input;
300 parser->input.string.current = input;
301 parser->input.string.end = input+size;
312 assert(!parser->read_handler);
315 parser->read_handler = yaml_file_read_handler;
316 parser->read_handler_data = parser;
318 parser->input.file =
file;
330 assert(!parser->read_handler);
333 parser->read_handler = handler;
334 parser->read_handler_data =
data;
345 assert(!parser->encoding);
347 parser->encoding = encoding;
368 if (!
STACK_INIT(emitter, emitter->indents,
int*))
382 STACK_DEL(emitter, emitter->tag_directives);
409 STACK_DEL(emitter, emitter->tag_directives);
420 yaml_string_write_handler(
void *
data,
unsigned char *buffer,
size_t size)
446 yaml_file_write_handler(
void *
data,
unsigned char *buffer,
size_t size)
450 return (fwrite(buffer, 1, size, emitter->
output.
file) == size);
458 unsigned char *output,
size_t size,
size_t *size_written)
461 assert(!emitter->write_handler);
464 emitter->write_handler = yaml_string_write_handler;
465 emitter->write_handler_data = emitter;
467 emitter->output.string.buffer = output;
468 emitter->output.string.size = size;
469 emitter->output.string.size_written = size_written;
481 assert(!emitter->write_handler);
484 emitter->write_handler = yaml_file_write_handler;
485 emitter->write_handler_data = emitter;
487 emitter->output.file =
file;
499 assert(!emitter->write_handler);
502 emitter->write_handler = handler;
503 emitter->write_handler_data =
data;
514 assert(!emitter->encoding);
516 emitter->encoding = encoding;
528 emitter->canonical = (canonical != 0);
540 emitter->best_indent = (1 < indent && indent < 10) ? indent : 2;
552 emitter->best_width = (width >= 0) ? width : -1;
564 emitter->unicode = (unicode != 0);
576 emitter->line_break = line_break;
591 yaml_free(token->data.tag_directive.handle);
592 yaml_free(token->data.tag_directive.prefix);
626 yaml_check_utf8(
const yaml_char_t *start,
size_t length)
631 while (pointer < end) {
638 width = (octet & 0x80) == 0x00 ? 1 :
639 (octet & 0xE0) == 0xC0 ? 2 :
640 (octet & 0xF0) == 0xE0 ? 3 :
641 (octet & 0xF8) == 0xF0 ? 4 : 0;
642 value = (octet & 0x80) == 0x00 ? octet & 0x7F :
643 (octet & 0xE0) == 0xC0 ? octet & 0x1F :
644 (octet & 0xF0) == 0xE0 ? octet & 0x0F :
645 (octet & 0xF8) == 0xF0 ? octet & 0x07 : 0;
646 if (!width)
return 0;
647 if (pointer+width > end)
return 0;
648 for (k = 1; k < width; k ++) {
650 if ((octet & 0xC0) != 0x80)
return 0;
651 value = (value << 6) + (octet & 0x3F);
653 if (!((width == 1) ||
654 (width == 2 && value >= 0x80) ||
655 (width == 3 && value >= 0x800) ||
656 (width == 4 && value >= 0x10000)))
return 0;
717 } tag_directives_copy = { NULL, NULL, NULL };
721 assert((tag_directives_start && tag_directives_end) ||
722 (tag_directives_start == tag_directives_end));
725 if (version_directive) {
727 if (!version_directive_copy)
goto error;
728 version_directive_copy->
major = version_directive->major;
729 version_directive_copy->
minor = version_directive->minor;
732 if (tag_directives_start != tag_directives_end) {
736 for (tag_directive = tag_directives_start;
737 tag_directive != tag_directives_end; tag_directive ++) {
738 assert(tag_directive->
handle);
739 assert(tag_directive->
prefix);
740 if (!yaml_check_utf8(tag_directive->
handle,
741 strlen((
char *)tag_directive->
handle)))
743 if (!yaml_check_utf8(tag_directive->
prefix,
744 strlen((
char *)tag_directive->
prefix)))
749 if (!
PUSH(&context, tag_directives_copy, value))
757 tag_directives_copy.start, tag_directives_copy.top,
758 implicit, mark, mark);
764 while (!
STACK_EMPTY(context, tag_directives_copy)) {
805 if (!yaml_check_utf8(anchor, strlen((
char *)anchor)))
return 0;
824 int plain_implicit,
int quoted_implicit,
836 if (!yaml_check_utf8(anchor, strlen((
char *)anchor)))
goto error;
838 if (!anchor_copy)
goto error;
842 if (!yaml_check_utf8(tag, strlen((
char *)tag)))
goto error;
844 if (!tag_copy)
goto error;
848 length = strlen((
char *)value);
851 if (!yaml_check_utf8(value, length))
goto error;
853 if (!value_copy)
goto error;
854 memcpy(value_copy, value, length);
855 value_copy[length] =
'\0';
858 plain_implicit, quoted_implicit, style, mark, mark);
886 if (!yaml_check_utf8(anchor, strlen((
char *)anchor)))
goto error;
888 if (!anchor_copy)
goto error;
892 if (!yaml_check_utf8(tag, strlen((
char *)tag)))
goto error;
894 if (!tag_copy)
goto error;
898 implicit, style, mark, mark);
941 if (!yaml_check_utf8(anchor, strlen((
char *)anchor)))
goto error;
943 if (!anchor_copy)
goto error;
947 if (!yaml_check_utf8(tag, strlen((
char *)tag)))
goto error;
949 if (!tag_copy)
goto error;
953 implicit, style, mark, mark);
994 yaml_free(event->data.document_start.version_directive);
995 for (tag_directive = event->data.document_start.tag_directives.start;
996 tag_directive != event->data.document_start.tag_directives.end;
1001 yaml_free(event->data.document_start.tag_directives.start);
1015 yaml_free(event->data.sequence_start.anchor);
1016 yaml_free(event->data.sequence_start.tag);
1020 yaml_free(event->data.mapping_start.anchor);
1021 yaml_free(event->data.mapping_start.tag);
1040 int start_implicit,
int end_implicit)
1049 } nodes = { NULL, NULL, NULL };
1055 } tag_directives_copy = { NULL, NULL, NULL };
1060 assert((tag_directives_start && tag_directives_end) ||
1061 (tag_directives_start == tag_directives_end));
1066 if (version_directive) {
1068 if (!version_directive_copy)
goto error;
1069 version_directive_copy->
major = version_directive->major;
1070 version_directive_copy->
minor = version_directive->minor;
1073 if (tag_directives_start != tag_directives_end) {
1077 for (tag_directive = tag_directives_start;
1078 tag_directive != tag_directives_end; tag_directive ++) {
1079 assert(tag_directive->
handle);
1080 assert(tag_directive->
prefix);
1081 if (!yaml_check_utf8(tag_directive->
handle,
1082 strlen((
char *)tag_directive->
handle)))
1084 if (!yaml_check_utf8(tag_directive->
prefix,
1085 strlen((
char *)tag_directive->
prefix)))
1090 if (!
PUSH(&context, tag_directives_copy, value))
1097 DOCUMENT_INIT(*document, nodes.start, nodes.end, version_directive_copy,
1098 tag_directives_copy.start, tag_directives_copy.top,
1099 start_implicit, end_implicit, mark, mark);
1106 while (!
STACK_EMPTY(&context, tag_directives_copy)) {
1111 STACK_DEL(&context, tag_directives_copy);
1132 switch (node.
type) {
1149 for (tag_directive = document->tag_directives.start;
1150 tag_directive != document->tag_directives.end;
1155 yaml_free(document->tag_directives.start);
1169 if (index > 0 && document->nodes.start + index <= document->nodes.top) {
1170 return document->nodes.start + index - 1;
1184 if (document->nodes.top != document->nodes.start) {
1185 return document->nodes.start;
1214 if (!yaml_check_utf8(tag, strlen((
char *)tag)))
goto error;
1216 if (!tag_copy)
goto error;
1219 length = strlen((
char *)value);
1222 if (!yaml_check_utf8(value, length))
goto error;
1224 if (!value_copy)
goto error;
1225 memcpy(value_copy, value, length);
1226 value_copy[length] =
'\0';
1229 if (!
PUSH(&context, document->nodes, node))
goto error;
1231 return document->nodes.top - document->nodes.start;
1257 } items = { NULL, NULL, NULL };
1266 if (!yaml_check_utf8(tag, strlen((
char *)tag)))
goto error;
1268 if (!tag_copy)
goto error;
1274 if (!
PUSH(&context, document->nodes, node))
goto error;
1276 return document->nodes.top - document->nodes.start;
1302 } pairs = { NULL, NULL, NULL };
1311 if (!yaml_check_utf8(tag, strlen((
char *)tag)))
goto error;
1313 if (!tag_copy)
goto error;
1319 if (!
PUSH(&context, document->nodes, node))
goto error;
1321 return document->nodes.top - document->nodes.start;
1336 int sequence,
int item)
1344 && document->nodes.start + sequence <= document->nodes.top);
1348 assert(item > 0 && document->nodes.start + item <= document->nodes.top);
1352 document->nodes.start[sequence-1].data.sequence.items, item))
1364 int mapping,
int key,
int value)
1374 && document->nodes.start + mapping <= document->nodes.top);
1378 assert(key > 0 && document->nodes.start + key <= document->nodes.top);
1380 assert(value > 0 && document->nodes.start + value <= document->nodes.top);
1387 document->nodes.start[mapping-1].data.mapping.pairs, pair))
#define MAPPING_START_EVENT_INIT(event, event_anchor, event_tag, event_implicit, event_style, start_mark, end_mark)
#define YAML_VERSION_PATCH
yaml_queue_extend(void **start, void **head, void **tail, void **end)
yaml_string_join(yaml_char_t **a_start, yaml_char_t **a_pointer, yaml_char_t **a_end, yaml_char_t **b_start, yaml_char_t **b_pointer, SHIM(yaml_char_t **b_end))
yaml_stream_end_event_initialize(yaml_event_t *event)
Create the STREAM-END event.
#define STREAM_END_EVENT_INIT(event, start_mark, end_mark)
yaml_event_delete(yaml_event_t *event)
Free any memory allocated for an event object.
#define INPUT_RAW_BUFFER_SIZE
enum yaml_encoding_e yaml_encoding_t
The stream encoding.
yaml_parser_set_encoding(yaml_parser_t *parser, yaml_encoding_t encoding)
Set the source encoding.
#define YAML_VERSION_MAJOR
struct yaml_node_s::@26::@27 scalar
The scalar parameters (for YAML_SCALAR_NODE).
enum yaml_sequence_style_e yaml_sequence_style_t
Sequence styles.
struct yaml_node_s::@26::@28 sequence
The sequence parameters (for YAML_SEQUENCE_NODE).
yaml_parser_set_input_string(yaml_parser_t *parser, const unsigned char *input, size_t size)
Set a string input.
int yaml_write_handler_t(void *data, unsigned char *buffer, size_t size)
The prototype of a write handler.
struct yaml_node_s::@26::@29 mapping
The mapping parameters (for YAML_MAPPING_NODE).
yaml_emitter_set_output(yaml_emitter_t *emitter, yaml_write_handler_t *handler, void *data)
Set a generic output handler.
#define STREAM_START_EVENT_INIT(event, event_encoding, start_mark, end_mark)
yaml_mapping_start_event_initialize(yaml_event_t *event, const yaml_char_t *anchor, const yaml_char_t *tag, int implicit, yaml_mapping_style_t style)
Create a MAPPING-START event.
int yaml_read_handler_t(void *data, unsigned char *buffer, size_t size, size_t *size_read)
The prototype of a read handler.
yaml_node_type_t type
The node type.
unsigned char yaml_char_t
The character type (UTF-8 octet).
The version directive data.
yaml_parser_delete(yaml_parser_t *parser)
Destroy a parser.
yaml_char_t * prefix
The tag prefix.
yaml_stream_start_event_initialize(yaml_event_t *event, yaml_encoding_t encoding)
Create the STREAM-START event.
yaml_emitter_set_break(yaml_emitter_t *emitter, yaml_break_t line_break)
Set the preferred line break.
union yaml_emitter_s::@45 output
Standard (string or file) output data.
An element of a mapping node.
#define PUSH(context, stack, value)
#define OUTPUT_RAW_BUFFER_SIZE
#define SCALAR_NODE_INIT(node, node_tag, node_value, node_length, node_style, start_mark, end_mark)
yaml_document_add_sequence(yaml_document_t *document, const yaml_char_t *tag, yaml_sequence_style_t style)
Create a SEQUENCE node and attach it to the document.
yaml_document_delete(yaml_document_t *document)
Delete a YAML document and all its nodes.
int yaml_node_item_t
An element of a sequence node.
#define SEQUENCE_END_EVENT_INIT(event, start_mark, end_mark)
yaml_document_append_mapping_pair(yaml_document_t *document, int mapping, int key, int value)
Add a pair of a key and a value to a MAPPING node.
yaml_document_append_sequence_item(yaml_document_t *document, int sequence, int item)
Add an item to a SEQUENCE node.
#define DEQUEUE(context, queue)
yaml_get_version_string(void)
Get the library version as a string.
#define STACK_EMPTY(context, stack)
int key
The key of the element.
#define DOCUMENT_INIT(document, document_nodes_start, document_nodes_end, document_version_directive, document_tag_directives_start, document_tag_directives_end, document_start_implicit, document_end_implicit, document_start_mark, document_end_mark)
FILE * file
File output data.
#define YAML_DEFAULT_SEQUENCE_TAG
The default sequence tag is !!seq.
union yaml_node_s::@26 data
The node data.
#define QUEUE_EMPTY(context, queue)
#define YAML_VERSION_MINOR
#define BUFFER_DEL(context, buffer)
#define OUTPUT_BUFFER_SIZE
yaml_emitter_set_encoding(yaml_emitter_t *emitter, yaml_encoding_t encoding)
Set the output encoding.
enum yaml_error_type_e yaml_error_type_t
Many bad things could happen with the parser and emitter.
#define MAPPING_NODE_INIT(node, node_tag, node_pairs_start, node_pairs_end, node_style, start_mark, end_mark)
int major
The major version number.
yaml_emitter_set_output_string(yaml_emitter_t *emitter, unsigned char *output, size_t size, size_t *size_written)
Set a string output.
yaml_char_t * tag
The node tag.
enum yaml_scalar_style_e yaml_scalar_style_t
Scalar styles.
struct yaml_emitter_s::@45::@55 string
String output data.
yaml_realloc(void *ptr, size_t size)
yaml_token_delete(yaml_token_t *token)
Free any memory allocated for a token object.
yaml_document_add_scalar(yaml_document_t *document, const yaml_char_t *tag, const yaml_char_t *value, int length, yaml_scalar_style_t style)
Create a SCALAR node and attach it to the document.
yaml_sequence_end_event_initialize(yaml_event_t *event)
Create a SEQUENCE-END event.
yaml_parser_set_input_file(yaml_parser_t *parser, FILE *file)
Set a file input.
#define ALIAS_EVENT_INIT(event, event_anchor, start_mark, end_mark)
yaml_document_get_node(yaml_document_t *document, int index)
Get a document node.
struct yaml_parser_s::@34::@44 string
String input data.
#define YAML_DECLARE(type)
The public API declaration.
#define STACK_DEL(context, stack)
yaml_strdup(const yaml_char_t *str)
#define BUFFER_INIT(context, buffer, size)
union yaml_parser_s::@34 input
Standard (string or file) input data.
yaml_parser_set_input(yaml_parser_t *parser, yaml_read_handler_t *handler, void *data)
Set a generic input handler.
#define DOCUMENT_END_EVENT_INIT(event, event_implicit, start_mark, end_mark)
#define MAPPING_END_EVENT_INIT(event, start_mark, end_mark)
yaml_document_initialize(yaml_document_t *document, yaml_version_directive_t *version_directive, yaml_tag_directive_t *tag_directives_start, yaml_tag_directive_t *tag_directives_end, int start_implicit, int end_implicit)
Create a YAML document.
#define SEQUENCE_START_EVENT_INIT(event, event_anchor, event_tag, event_implicit, event_style, start_mark, end_mark)
yaml_char_t * handle
The tag handle.
#define QUEUE_INIT(context, queue, size, type)
yaml_document_end_event_initialize(yaml_event_t *event, int implicit)
Create the DOCUMENT-END event.
enum yaml_emitter_state_e yaml_emitter_state_t
The emitter states.
yaml_emitter_set_width(yaml_emitter_t *emitter, int width)
Set the preferred line width.
yaml_stack_extend(void **start, void **top, void **end)
yaml_emitter_set_canonical(yaml_emitter_t *emitter, int canonical)
Set if the output should be in the "canonical" format as in the YAML specification.
int value
The value of the element.
#define QUEUE_DEL(context, queue)
yaml_node_item_t * start
The beginning of the stack.
yaml_document_start_event_initialize(yaml_event_t *event, yaml_version_directive_t *version_directive, yaml_tag_directive_t *tag_directives_start, yaml_tag_directive_t *tag_directives_end, int implicit)
Create the DOCUMENT-START event.
yaml_document_add_mapping(yaml_document_t *document, const yaml_char_t *tag, yaml_mapping_style_t style)
Create a MAPPING node and attach it to the document.
yaml_emitter_set_unicode(yaml_emitter_t *emitter, int unicode)
Set if unescaped non-ASCII characters are allowed.
FILE * file
File input data.
#define INITIAL_QUEUE_SIZE
#define YAML_MALLOC(size)
yaml_sequence_start_event_initialize(yaml_event_t *event, const yaml_char_t *anchor, const yaml_char_t *tag, int implicit, yaml_sequence_style_t style)
Create a SEQUENCE-START event.
#define YAML_DEFAULT_SCALAR_TAG
The default scalar tag is !!str.
This structure holds information about a potential simple key.
#define YAML_MALLOC_STATIC(type)
enum yaml_parser_state_e yaml_parser_state_t
The states of the parser.
#define YAML_VERSION_STRING
yaml_parser_initialize(yaml_parser_t *parser)
Initialize a parser.
int minor
The minor version number.
yaml_string_extend(yaml_char_t **start, yaml_char_t **pointer, yaml_char_t **end)
yaml_alias_event_initialize(yaml_event_t *event, const yaml_char_t *anchor)
Create an ALIAS event.
#define POP(context, stack)
yaml_emitter_set_output_file(yaml_emitter_t *emitter, FILE *file)
Set a file output.
#define INPUT_BUFFER_SIZE
#define DOCUMENT_START_EVENT_INIT(event, event_version_directive, event_tag_directives_start, event_tag_directives_end, event_implicit, start_mark, end_mark)
yaml_mapping_end_event_initialize(yaml_event_t *event)
Create a MAPPING-END event.
#define SEQUENCE_NODE_INIT(node, node_tag, node_items_start, node_items_end, node_style, start_mark, end_mark)
yaml_scalar_event_initialize(yaml_event_t *event, const yaml_char_t *anchor, const yaml_char_t *tag, const yaml_char_t *value, int length, int plain_implicit, int quoted_implicit, yaml_scalar_style_t style)
Create a SCALAR event.
yaml_emitter_set_indent(yaml_emitter_t *emitter, int indent)
Set the indentation increment.
#define YAML_DEFAULT_MAPPING_TAG
The default mapping tag is !!map.
yaml_get_version(int *major, int *minor, int *patch)
Get the library version numbers.
enum yaml_mapping_style_e yaml_mapping_style_t
Mapping styles.
#define SCALAR_EVENT_INIT(event, event_anchor, event_tag, event_value, event_length, event_plain_implicit, event_quoted_implicit, event_style, start_mark, end_mark)
yaml_emitter_initialize(yaml_emitter_t *emitter)
Initialize an emitter.
#define STACK_INIT(context, stack, type)
yaml_emitter_delete(yaml_emitter_t *emitter)
Destroy an emitter.
yaml_document_get_root_node(yaml_document_t *document)
Get the root object.
enum yaml_break_e yaml_break_t
Line break types.