]> andersk Git - libyaml.git/blame - src/api.c
The scanner is completed (not tested though).
[libyaml.git] / src / api.c
CommitLineData
a51447c9
KS
1
2#if HAVE_CONFIG_H
3#include <config.h>
4#endif
5
6#include <yaml/yaml.h>
7
95b98ba9
KS
8#include <assert.h>
9
10/*
11 * Allocate a dynamic memory block.
12 */
13
f642fd11 14YAML_DECLARE(void *)
95b98ba9
KS
15yaml_malloc(size_t size)
16{
17 return malloc(size ? size : 1);
18}
19
20/*
21 * Reallocate a dynamic memory block.
22 */
23
f642fd11 24YAML_DECLARE(void *)
95b98ba9
KS
25yaml_realloc(void *ptr, size_t size)
26{
27 return ptr ? realloc(ptr, size ? size : 1) : malloc(size ? size : 1);
28}
29
a51447c9 30/*
95b98ba9
KS
31 * Free a dynamic memory block.
32 */
33
f642fd11 34YAML_DECLARE(void)
95b98ba9
KS
35yaml_free(void *ptr)
36{
37 if (ptr) free(ptr);
38}
39
40/*
41 * Create a new parser object.
a51447c9
KS
42 */
43
f642fd11 44YAML_DECLARE(yaml_parser_t *)
a51447c9
KS
45yaml_parser_new(void)
46{
47 yaml_parser_t *parser;
48
6eb1ded4
KS
49 /* Allocate the parser structure. */
50
95b98ba9 51 parser = yaml_malloc(sizeof(yaml_parser_t));
f2b59d4d 52 if (!parser) goto error;
a51447c9
KS
53
54 memset(parser, 0, sizeof(yaml_parser_t));
55
6eb1ded4
KS
56 /* Allocate the raw buffer. */
57
58 parser->raw_buffer = yaml_malloc(YAML_RAW_BUFFER_SIZE);
f2b59d4d
KS
59 if (!parser->raw_buffer) goto error;
60 memset(parser->raw_buffer, 0, YAML_RAW_BUFFER_SIZE);
61
6eb1ded4
KS
62 parser->raw_pointer = parser->raw_buffer;
63 parser->raw_unread = 0;
64
65 /* Allocate the character buffer. */
66
67 parser->buffer = yaml_malloc(YAML_BUFFER_SIZE);
f2b59d4d
KS
68 if (!parser->buffer) goto error;
69 memset(parser->buffer, 0, YAML_BUFFER_SIZE);
70
6eb1ded4
KS
71 parser->buffer_end = parser->buffer;
72 parser->pointer = parser->buffer;
73 parser->unread = 0;
74
f2b59d4d
KS
75 /* Allocate the tokens queue. */
76
77 parser->tokens = yaml_malloc(YAML_DEFAULT_SIZE*sizeof(yaml_token_t *));
78 if (!parser->tokens) goto error;
79 memset(parser->tokens, 0, YAML_DEFAULT_SIZE*sizeof(yaml_token_t *));
80
81 parser->tokens_size = YAML_DEFAULT_SIZE;
82 parser->tokens_head = 0;
83 parser->tokens_tail = 0;
84 parser->tokens_parsed = 0;
85
86 /* Allocate the indents stack. */
87
88 parser->indents = yaml_malloc(YAML_DEFAULT_SIZE*sizeof(int));
89 if (!parser->indents) goto error;
90 memset(parser->indents, 0, YAML_DEFAULT_SIZE*sizeof(int));
91
92 parser->indents_size = YAML_DEFAULT_SIZE;
93 parser->indents_length = 0;
94
95 /* Allocate the stack of potential simple keys. */
96
97 parser->simple_keys = yaml_malloc(YAML_DEFAULT_SIZE*sizeof(yaml_simple_key_t *));
98 if (!parser->simple_keys) goto error;
99 memset(parser->simple_keys, 0, YAML_DEFAULT_SIZE*sizeof(yaml_simple_key_t *));
100
101 parser->simple_keys_size = YAML_DEFAULT_SIZE;
102
103 /* Done. */
104
a51447c9 105 return parser;
f2b59d4d
KS
106
107 /* On error, free allocated buffers. */
108
109error:
110
111 if (!parser) return NULL;
112
113 yaml_free(parser->simple_keys);
114 yaml_free(parser->indents);
115 yaml_free(parser->tokens);
116 yaml_free(parser->buffer);
117 yaml_free(parser->raw_buffer);
118
119 yaml_free(parser);
120
121 return NULL;
a51447c9
KS
122}
123
124/*
125 * Destroy a parser object.
126 */
127
f642fd11 128YAML_DECLARE(void)
a51447c9
KS
129yaml_parser_delete(yaml_parser_t *parser)
130{
95b98ba9
KS
131 assert(parser); /* Non-NULL parser object expected. */
132
f2b59d4d
KS
133 yaml_free(parser->simple_keys);
134 yaml_free(parser->indents);
135 yaml_free(parser->tokens);
95b98ba9 136 yaml_free(parser->buffer);
6eb1ded4 137 yaml_free(parser->raw_buffer);
95b98ba9
KS
138
139 memset(parser, 0, sizeof(yaml_parser_t));
140
141 yaml_free(parser);
142}
143
144/*
6eb1ded4 145 * String read handler.
95b98ba9
KS
146 */
147
148static int
149yaml_string_read_handler(void *data, unsigned char *buffer, size_t size,
150 size_t *size_read)
151{
6eb1ded4
KS
152 yaml_string_input_t *input = data;
153
154 if (input->current == input->end) {
155 *size_read = 0;
156 return 1;
157 }
158
159 if (size > (input->end - input->current)) {
160 size = input->end - input->current;
161 }
162
163 memcpy(buffer, input->current, size);
164 input->current += size;
165 *size_read = size;
95b98ba9
KS
166 return 1;
167}
168
169/*
170 * File read handler.
171 */
172
173static int
174yaml_file_read_handler(void *data, unsigned char *buffer, size_t size,
175 size_t *size_read)
176{
6eb1ded4
KS
177 *size_read = fread(buffer, 1, size, (FILE *)data);
178 return !ferror((FILE *)data);
95b98ba9
KS
179}
180
181/*
182 * Set a string input.
183 */
184
f642fd11 185YAML_DECLARE(void)
95b98ba9
KS
186yaml_parser_set_input_string(yaml_parser_t *parser,
187 unsigned char *input, size_t size)
188{
189 assert(parser); /* Non-NULL parser object expected. */
6eb1ded4 190 assert(!parser->read_handler); /* You can set the source only once. */
95b98ba9
KS
191 assert(input); /* Non-NULL input string expected. */
192
6eb1ded4
KS
193 parser->string_input.start = input;
194 parser->string_input.current = input;
195 parser->string_input.end = input+size;
95b98ba9 196
6eb1ded4
KS
197 parser->read_handler = yaml_string_read_handler;
198 parser->read_handler_data = &parser->string_input;
95b98ba9
KS
199}
200
201/*
202 * Set a file input.
203 */
204
f642fd11 205YAML_DECLARE(void)
95b98ba9
KS
206yaml_parser_set_input_file(yaml_parser_t *parser, FILE *file)
207{
208 assert(parser); /* Non-NULL parser object expected. */
6eb1ded4 209 assert(!parser->read_handler); /* You can set the source only once. */
95b98ba9
KS
210 assert(file); /* Non-NULL file object expected. */
211
212 parser->read_handler = yaml_file_read_handler;
213 parser->read_handler_data = file;
214}
215
216/*
217 * Set a generic input.
218 */
219
f642fd11 220YAML_DECLARE(void)
95b98ba9
KS
221yaml_parser_set_input(yaml_parser_t *parser,
222 yaml_read_handler_t *handler, void *data)
223{
224 assert(parser); /* Non-NULL parser object expected. */
6eb1ded4 225 assert(!parser->read_handler); /* You can set the source only once. */
95b98ba9
KS
226 assert(handler); /* Non-NULL read handler expected. */
227
228 parser->read_handler = handler;
6eb1ded4 229 parser->read_handler_data = data;
95b98ba9
KS
230}
231
232/*
233 * Set the source encoding.
234 */
235
f642fd11 236YAML_DECLARE(void)
95b98ba9
KS
237yaml_parser_set_encoding(yaml_parser_t *parser, yaml_encoding_t encoding)
238{
239 assert(parser); /* Non-NULL parser object expected. */
240 assert(!parser->encoding); /* Encoding is already set or detected. */
241
242 parser->encoding = encoding;
a51447c9
KS
243}
244
f642fd11
KS
245/*
246 * Create a token.
247 */
248
249YAML_DECLARE(yaml_token_t *)
250yaml_token_new(yaml_token_type_t type,
251 yaml_mark_t start_mark, yaml_mark_t end_mark)
252{
253 yaml_token_t *token = yaml_malloc(sizeof(yaml_token_t));
254
255 if (!token) return NULL;
256
257 memset(token, 0, sizeof(yaml_token_t));
258
259 token->type = type;
260 token->start_mark = start_mark;
261 token->end_mark = end_mark;
262
263 return token;
264}
265
266/*
267 * Create a STREAM-START token.
268 */
269
270YAML_DECLARE(yaml_token_t *)
21fbedd4 271yaml_stream_start_token_new(yaml_encoding_t encoding,
f642fd11
KS
272 yaml_mark_t start_mark, yaml_mark_t end_mark)
273{
274 yaml_token_t *token = yaml_token_new(YAML_STREAM_START_TOKEN,
275 start_mark, end_mark);
276
277 if (!token) return NULL;
278
279 token->data.encoding = encoding;
280
281 return token;
282}
283
284/*
285 * Create a STREAM-END token.
286 */
287
288YAML_DECLARE(yaml_token_t *)
21fbedd4 289yaml_stream_end_token_new(yaml_mark_t start_mark, yaml_mark_t end_mark)
f642fd11
KS
290{
291 yaml_token_t *token = yaml_token_new(YAML_STREAM_END_TOKEN,
292 start_mark, end_mark);
293
294 if (!token) return NULL;
295
296 return token;
297}
298
299/*
300 * Create a VERSION-DIRECTIVE token.
301 */
302
303YAML_DECLARE(yaml_token_t *)
304yaml_version_directive_token_new(int major, int minor,
305 yaml_mark_t start_mark, yaml_mark_t end_mark)
306{
307 yaml_token_t *token = yaml_token_new(YAML_VERSION_DIRECTIVE_TOKEN,
308 start_mark, end_mark);
309
310 if (!token) return NULL;
311
312 token->data.version_directive.major = major;
313 token->data.version_directive.minor = minor;
314
315 return token;
316}
317
318/*
319 * Create a TAG-DIRECTIVE token.
320 */
321
322YAML_DECLARE(yaml_token_t *)
323yaml_tag_directive_token_new(yaml_char_t *handle, yaml_char_t *prefix,
324 yaml_mark_t start_mark, yaml_mark_t end_mark)
325{
326 yaml_token_t *token = yaml_token_new(YAML_TAG_DIRECTIVE_TOKEN,
327 start_mark, end_mark);
328
329 if (!token) return NULL;
330
331 token->data.tag_directive.handle = handle;
332 token->data.tag_directive.prefix = prefix;
333
334 return token;
335}
336
337/*
338 * Create an ALIAS token.
339 */
340
341YAML_DECLARE(yaml_token_t *)
342yaml_alias_token_new(yaml_char_t *anchor,
343 yaml_mark_t start_mark, yaml_mark_t end_mark)
344{
345 yaml_token_t *token = yaml_token_new(YAML_ALIAS_TOKEN,
346 start_mark, end_mark);
347
348 if (!token) return NULL;
349
350 token->data.anchor = anchor;
351
352 return token;
353}
354
355/*
356 * Create an ANCHOR token.
357 */
358
359YAML_DECLARE(yaml_token_t *)
360yaml_anchor_token_new(yaml_char_t *anchor,
361 yaml_mark_t start_mark, yaml_mark_t end_mark)
362{
363 yaml_token_t *token = yaml_token_new(YAML_ANCHOR_TOKEN,
364 start_mark, end_mark);
365
366 if (!token) return NULL;
367
368 token->data.anchor = anchor;
369
370 return token;
371}
372
373/*
374 * Create a TAG token.
375 */
376
377YAML_DECLARE(yaml_token_t *)
378yaml_tag_token_new(yaml_char_t *handle, yaml_char_t *suffix,
379 yaml_mark_t start_mark, yaml_mark_t end_mark)
380{
381 yaml_token_t *token = yaml_token_new(YAML_TAG_TOKEN,
382 start_mark, end_mark);
383
384 if (!token) return NULL;
385
386 token->data.tag.handle = handle;
387 token->data.tag.suffix = suffix;
388
389 return token;
390}
391
392/*
393 * Create a SCALAR token.
394 */
395
396YAML_DECLARE(yaml_token_t *)
397yaml_scalar_token_new(yaml_char_t *value, size_t length,
398 yaml_scalar_style_t style,
399 yaml_mark_t start_mark, yaml_mark_t end_mark)
400{
401 yaml_token_t *token = yaml_token_new(YAML_SCALAR_TOKEN,
402 start_mark, end_mark);
403
404 if (!token) return NULL;
405
406 token->data.scalar.value = value;
407 token->data.scalar.length = length;
408 token->data.scalar.style = style;
409
410 return token;
411}
412
413/*
414 * Destroy a token object.
415 */
416
417YAML_DECLARE(void)
418yaml_token_delete(yaml_token_t *token)
419{
420 assert(token); /* Non-NULL token object expected. */
421
422 switch (token->type)
423 {
424 case YAML_TAG_DIRECTIVE_TOKEN:
425 yaml_free(token->data.tag_directive.handle);
426 yaml_free(token->data.tag_directive.prefix);
427 break;
428
429 case YAML_ALIAS_TOKEN:
430 case YAML_ANCHOR_TOKEN:
431 yaml_free(token->data.anchor);
432 break;
433
434 case YAML_TAG_TOKEN:
435 yaml_free(token->data.tag.handle);
436 yaml_free(token->data.tag.suffix);
437 break;
438
439 case YAML_SCALAR_TOKEN:
440 yaml_free(token->data.scalar.value);
441 break;
442 }
443
444 memset(token, 0, sizeof(yaml_token_t));
445
446 yaml_free(token);
447}
448
This page took 0.104468 seconds and 5 git commands to generate.