LCOV - code coverage report
Current view: top level - lib - ovsdb-parser.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 57 65 87.7 %
Date: 2016-09-14 01:02:56 Functions: 8 8 100.0 %
Branches: 33 54 61.1 %

           Branch data     Line data    Source code
       1                 :            : /* Copyright (c) 2009, 2011, 2013, 2015 Nicira, Inc.
       2                 :            :  *
       3                 :            :  * Licensed under the Apache License, Version 2.0 (the "License");
       4                 :            :  * you may not use this file except in compliance with the License.
       5                 :            :  * You may obtain a copy of the License at:
       6                 :            :  *
       7                 :            :  *     http://www.apache.org/licenses/LICENSE-2.0
       8                 :            :  *
       9                 :            :  * Unless required by applicable law or agreed to in writing, software
      10                 :            :  * distributed under the License is distributed on an "AS IS" BASIS,
      11                 :            :  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
      12                 :            :  * See the License for the specific language governing permissions and
      13                 :            :  * limitations under the License.
      14                 :            :  */
      15                 :            : 
      16                 :            : #include <config.h>
      17                 :            : 
      18                 :            : #include "ovsdb-parser.h"
      19                 :            : 
      20                 :            : #include <ctype.h>
      21                 :            : #include <stdarg.h>
      22                 :            : 
      23                 :            : #include "ovsdb-error.h"
      24                 :            : 
      25                 :            : void
      26                 :     884397 : ovsdb_parser_init(struct ovsdb_parser *parser, const struct json *json,
      27                 :            :                   const char *name, ...)
      28                 :            : {
      29                 :            :     va_list args;
      30                 :            : 
      31                 :     884397 :     va_start(args, name);
      32                 :     884397 :     parser->name = xvasprintf(name, args);
      33                 :     884397 :     va_end(args);
      34                 :            : 
      35                 :     884397 :     sset_init(&parser->used);
      36                 :     884397 :     parser->error = NULL;
      37                 :            : 
      38 [ +  - ][ +  - ]:     884397 :     parser->json = (json && json->type == JSON_OBJECT ? json : NULL);
      39         [ -  + ]:     884397 :     if (!parser->json) {
      40                 :          0 :         ovsdb_parser_raise_error(parser, "Object expected.");
      41                 :            :     }
      42                 :     884397 : }
      43                 :            : 
      44                 :            : bool
      45                 :     529605 : ovsdb_parser_is_id(const char *string)
      46                 :            : {
      47                 :            :     unsigned char c;
      48                 :            : 
      49                 :     529605 :     c = *string;
      50 [ +  + ][ +  - ]:     529605 :     if (!isalpha(c) && c != '_') {
      51                 :          2 :         return false;
      52                 :            :     }
      53                 :            : 
      54                 :            :     for (;;) {
      55                 :    5357064 :         c = *++string;
      56         [ +  + ]:    5357064 :         if (c == '\0') {
      57                 :     529602 :             return true;
      58 [ +  + ][ +  + ]:    4827462 :         } else if (!isalpha(c) && !isdigit(c) && c != '_') {
                 [ +  + ]
      59                 :          1 :             return false;
      60                 :            :         }
      61                 :    4827461 :     }
      62                 :            : }
      63                 :            : 
      64                 :            : const struct json *
      65                 :    2918549 : ovsdb_parser_member(struct ovsdb_parser *parser, const char *name,
      66                 :            :                     enum ovsdb_parser_types types)
      67                 :            : {
      68                 :            :     struct json *value;
      69                 :            : 
      70         [ -  + ]:    2918549 :     if (!parser->json) {
      71                 :          0 :         return NULL;
      72                 :            :     }
      73                 :            : 
      74                 :    2918549 :     value = shash_find_data(json_object(parser->json), name);
      75         [ +  + ]:    2918549 :     if (!value) {
      76         [ +  + ]:    1090251 :         if (!(types & OP_OPTIONAL)) {
      77                 :          4 :             ovsdb_parser_raise_error(parser,
      78                 :            :                                      "Required '%s' member is missing.", name);
      79                 :            :         }
      80                 :    1090251 :         return NULL;
      81                 :            :     }
      82                 :            : 
      83 [ +  - ][ +  - ]:    1828298 :     if (((int) value->type >= 0 && value->type < JSON_N_TYPES
      84         [ +  + ]:    1828298 :          && types & (1u << value->type))
      85 [ +  - ][ +  - ]:     211737 :         || (types & OP_ID && value->type == JSON_STRING
      86         [ +  + ]:     211737 :             && ovsdb_parser_is_id(value->u.string)))
      87                 :            :     {
      88                 :    1828296 :         sset_add(&parser->used, name);
      89                 :    1828296 :         return value;
      90                 :            :     } else {
      91                 :          2 :         ovsdb_parser_raise_error(parser, "Type mismatch for member '%s'.",
      92                 :            :                                  name);
      93                 :          2 :         return NULL;
      94                 :            :     }
      95                 :            : }
      96                 :            : 
      97                 :            : void
      98                 :          6 : ovsdb_parser_raise_error(struct ovsdb_parser *parser, const char *format, ...)
      99                 :            : {
     100         [ +  - ]:          6 :     if (!parser->error) {
     101                 :            :         struct ovsdb_error *error;
     102                 :            :         va_list args;
     103                 :            :         char *message;
     104                 :            : 
     105                 :          6 :         va_start(args, format);
     106                 :          6 :         message = xvasprintf(format, args);
     107                 :          6 :         va_end(args);
     108                 :            : 
     109                 :          6 :         error = ovsdb_syntax_error(parser->json, NULL, "Parsing %s failed: %s",
     110                 :            :                                    parser->name, message);
     111                 :          6 :         free(message);
     112                 :            : 
     113                 :          6 :         parser->error = error;
     114                 :            :     }
     115                 :          6 : }
     116                 :            : 
     117                 :            : struct ovsdb_error *
     118                 :      68451 : ovsdb_parser_get_error(const struct ovsdb_parser *parser)
     119                 :            : {
     120         [ +  + ]:      68451 :     return parser->error ? ovsdb_error_clone(parser->error) : NULL;
     121                 :            : }
     122                 :            : 
     123                 :            : bool
     124                 :     116394 : ovsdb_parser_has_error(const struct ovsdb_parser *parser)
     125                 :            : {
     126                 :     116394 :     return parser->error != NULL;
     127                 :            : }
     128                 :            : 
     129                 :            : struct ovsdb_error *
     130                 :     884397 : ovsdb_parser_destroy(struct ovsdb_parser *parser)
     131                 :            : {
     132                 :     884397 :     free(parser->name);
     133                 :     884397 :     sset_destroy(&parser->used);
     134                 :            : 
     135                 :     884397 :     return parser->error;
     136                 :            : }
     137                 :            : 
     138                 :            : struct ovsdb_error *
     139                 :     767556 : ovsdb_parser_finish(struct ovsdb_parser *parser)
     140                 :            : {
     141         [ +  + ]:     767556 :     if (!parser->error) {
     142                 :     767550 :         const struct shash *object = json_object(parser->json);
     143                 :            :         size_t n_unused;
     144                 :            : 
     145                 :     767550 :         n_unused = shash_count(object) - sset_count(&parser->used);
     146         [ -  + ]:     767550 :         if (n_unused) {
     147                 :            :             struct shash_node *node;
     148                 :            : 
     149 [ #  # ][ #  # ]:          0 :             SHASH_FOR_EACH (node, object) {
     150         [ #  # ]:          0 :                 if (!sset_contains(&parser->used, node->name)) {
     151         [ #  # ]:          0 :                     if (n_unused > 1) {
     152         [ #  # ]:          0 :                         ovsdb_parser_raise_error(
     153                 :            :                             parser,
     154                 :            :                             "Member '%s' and %"PRIuSIZE" other member%s "
     155                 :            :                             "are present but not allowed here.",
     156                 :            :                             node->name, n_unused - 1, n_unused > 2 ? "s" : "");
     157                 :            :                     } else {
     158                 :          0 :                         ovsdb_parser_raise_error(
     159                 :            :                             parser,
     160                 :            :                             "Member '%s' is present but not allowed here.",
     161                 :            :                             node->name);
     162                 :            :                     }
     163                 :          0 :                     break;
     164                 :            :                 }
     165                 :            :             }
     166                 :            :         }
     167                 :            :     }
     168                 :            : 
     169                 :     767556 :     return ovsdb_parser_destroy(parser);
     170                 :            : }

Generated by: LCOV version 1.12