1/* 2 * JSON streaming support 3 * 4 * Copyright IBM, Corp. 2009 5 * 6 * Authors: 7 * Anthony Liguori <aliguori@us.ibm.com> 8 * 9 * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 * See the COPYING.LIB file in the top-level directory. 11 * 12 */ 13 14#include "qlist.h" 15#include "qint.h" 16#include "qdict.h" 17#include "qemu-common.h" 18#include "json-lexer.h" 19#include "json-streamer.h" 20 21static void json_message_process_token(JSONLexer *lexer, QString *token, JSONTokenType type, int x, int y) 22{ 23 JSONMessageParser *parser = container_of(lexer, JSONMessageParser, lexer); 24 QDict *dict; 25 26 if (type == JSON_OPERATOR) { 27 switch (qstring_get_str(token)[0]) { 28 case '{': 29 parser->brace_count++; 30 break; 31 case '}': 32 parser->brace_count--; 33 break; 34 case '[': 35 parser->bracket_count++; 36 break; 37 case ']': 38 parser->bracket_count--; 39 break; 40 default: 41 break; 42 } 43 } 44 45 dict = qdict_new(); 46 qdict_put(dict, "type", qint_from_int(type)); 47 QINCREF(token); 48 qdict_put(dict, "token", token); 49 qdict_put(dict, "x", qint_from_int(x)); 50 qdict_put(dict, "y", qint_from_int(y)); 51 52 qlist_append(parser->tokens, dict); 53 54 if (parser->brace_count == 0 && 55 parser->bracket_count == 0) { 56 parser->emit(parser, parser->tokens); 57 QDECREF(parser->tokens); 58 parser->tokens = qlist_new(); 59 } 60} 61 62void json_message_parser_init(JSONMessageParser *parser, 63 void (*func)(JSONMessageParser *, QList *)) 64{ 65 parser->emit = func; 66 parser->brace_count = 0; 67 parser->bracket_count = 0; 68 parser->tokens = qlist_new(); 69 70 json_lexer_init(&parser->lexer, json_message_process_token); 71} 72 73int json_message_parser_feed(JSONMessageParser *parser, 74 const char *buffer, size_t size) 75{ 76 return json_lexer_feed(&parser->lexer, buffer, size); 77} 78 79int json_message_parser_flush(JSONMessageParser *parser) 80{ 81 return json_lexer_flush(&parser->lexer); 82} 83 84void json_message_parser_destroy(JSONMessageParser *parser) 85{ 86 json_lexer_destroy(&parser->lexer); 87 QDECREF(parser->tokens); 88} 89