else:
return cType
+def is_string_map(column):
+ return (column.type.key
+ and column.type.value
+ and column.type.key.type == ovs.db.types.StringType
+ and column.type.value.type == ovs.db.types.StringType)
+
def cMembers(prefix, columnName, column, const):
type = column.type
- if is_optional_bool(type):
- const = True
if type.n_min == 1 and type.n_max == 1:
singleton = True
pointer = ''
in cMembers(prefix, columnName, column, True)]
print '%s);' % ', '.join(args)
+ print
+ for columnName, column in sorted(table.columns.iteritems()):
+ if not is_string_map(column):
+ continue
+ print "const char *%(s)s_get_%(c)s_value(const struct %(s)s *," \
+ " const char *key, const char *default_value);" \
+ % {'s': structName, 'c': columnName}
+
+
# Table indexes.
printEnum(["%sTABLE_%s" % (prefix.upper(), tableName.upper()) for tableName in sorted(schema.tables)] + ["%sN_TABLES" % prefix.upper()])
print
print " %s" % members[-1]
print "};"
-def is_optional_bool(type):
- return (type.key.type == ovs.db.types.BooleanType and not type.value
- and type.n_min == 0 and type.n_max == 1)
-
def printCIDLSource(schemaFile):
schema = parseSchema(schemaFile)
prefix = schema.idlPrefix
#include "ovsdb-data.h"
#include "ovsdb-error.h"
+#ifdef __CHECKER__
+/* Sparse dislikes sizeof(bool) ("warning: expression using sizeof bool"). */
+enum { sizeof_bool = 1 };
+#else
+enum { sizeof_bool = sizeof(bool) };
+#endif
+
static bool inited;
''' % schema.idlHeader
+ try:
+ for table in schema.tables.itervalues():
+ for column in table.columns.itervalues():
+ if is_string_map(column):
+ print """\
+static int
+bsearch_strcmp(const void *a_, const void *b_)
+{
+ char *const *a = a_;
+ char *const *b = b_;
+ return strcmp(*a, *b);
+}"""
+ raise StopIteration
+ except StopIteration:
+ pass
+
# Cast functions.
for tableName, table in sorted(schema.tables.iteritems()):
structName = "%s%s" % (prefix, tableName.lower())
keyVar = "row->%s" % columnName
valueVar = None
- if is_optional_bool(type):
- # Special case for an optional bool. This is only here because
- # sparse does not like the "normal" case below ("warning:
- # expression using sizeof bool").
- print
- print " assert(inited);"
- print " if (datum->n >= 1) {"
- print " static const bool false_value = false;"
- print " static const bool true_value = true;"
- print
- print " row->n_%s = 1;" % columnName
- print " %s = datum->keys[0].boolean ? &true_value : &false_value;" % keyVar
- print " } else {"
- print " row->n_%s = 0;" % columnName
- print " %s = NULL;" % keyVar
- print " }"
- elif (type.n_min == 1 and type.n_max == 1) or type.is_optional_pointer():
+ if (type.n_min == 1 and type.n_max == 1) or type.is_optional_pointer():
print
print " assert(inited);"
print " if (datum->n >= 1) {"
else:
indent = " "
print "%sif (!row->n_%s) {" % (indent, columnName)
- print "%s %s = xmalloc(%s * sizeof *%s);" % (indent, keyVar, nMax, keyVar)
+
+ # Special case for boolean types. This is only here because
+ # sparse does not like the "normal" case ("warning: expression
+ # using sizeof bool").
+ if type.key.type == ovs.db.types.BooleanType:
+ sizeof = "sizeof_bool"
+ else:
+ sizeof = "sizeof *%s" % keyVar
+ print "%s %s = xmalloc(%s * %s);" % (indent, keyVar, nMax,
+ sizeof)
if valueVar:
- print "%s %s = xmalloc(%s * sizeof *%s);" % (indent, valueVar, nMax, valueVar)
+ # Special case for boolean types (see above).
+ if type.value.type == ovs.db.types.BooleanType:
+ sizeof = " * sizeof_bool"
+ else:
+ sizeof = "sizeof *%s" % valueVar
+ print "%s %s = xmalloc(%s * %s);" % (indent, valueVar,
+ nMax, sizeof)
print "%s}" % indent
print "%s%s[row->n_%s] = %s;" % (indent, keyVar, columnName, keySrc)
if valueVar:
# Unparse functions.
for columnName, column in sorted(table.columns.iteritems()):
type = column.type
- if (type.key.type == ovs.db.types.BooleanType and not type.value
- and type.n_min == 0 and type.n_max == 1):
- print '''
-static void
-%(s)s_unparse_%(c)s(struct ovsdb_idl_row *row OVS_UNUSED)
-{
- /* Nothing to do. */
-}''' % {'s': structName, 'c': columnName}
- elif (type.n_min != 1 or type.n_max != 1) and not type.is_optional_pointer():
+ if (type.n_min != 1 or type.n_max != 1) and not type.is_optional_pointer():
print '''
static void
%(s)s_unparse_%(c)s(struct ovsdb_idl_row *row_)
'C': columnName.upper()}
print "}"
+ # String Map Helpers.
+ for columnName, column in sorted(table.columns.iteritems()):
+ if not is_string_map(column):
+ continue
+
+ print """
+const char * %(s)s_get_%(c)s_value(const struct %(s)s *row, const char *search_key, const char *default_value)
+{
+ char **keys = row->key_%(c)s;
+ char **values = row->value_%(c)s;
+ size_t n_keys = row->n_%(c)s;
+ char ** result_key;
+
+ assert(inited);
+ result_key = bsearch(&search_key, keys, n_keys, sizeof *keys,
+ bsearch_strcmp);
+ return result_key ? values[result_key - keys] : default_value;
+}""" % {'s': structName, 'c': columnName}
+
# Table columns.
print "\nstruct ovsdb_idl_column %s_columns[%s_N_COLUMNS];" % (
structName, structName.upper())