diff options
author | ISHIDA Wataru <ishida.wataru@lab.ntt.co.jp> | 2016-01-23 17:18:56 +0900 |
---|---|---|
committer | FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> | 2016-01-25 04:57:11 -0800 |
commit | d94f5d2c03b8eb265cfa1af5dce43da7194538b8 (patch) | |
tree | 94872abec34c97a19c9abe457b10217d8c44964a /tools/pyang_plugins | |
parent | 3817b82f9d57ce02adb025f5acff6f06b54c6641 (diff) |
config: add openconfig identity structs in bgp_configs.go
Signed-off-by: ISHIDA Wataru <ishida.wataru@lab.ntt.co.jp>
Diffstat (limited to 'tools/pyang_plugins')
-rw-r--r-- | tools/pyang_plugins/bgpyang2golang.py | 151 | ||||
-rw-r--r-- | tools/pyang_plugins/gobgp.yang | 69 |
2 files changed, 153 insertions, 67 deletions
diff --git a/tools/pyang_plugins/bgpyang2golang.py b/tools/pyang_plugins/bgpyang2golang.py index 64d4d97c..45a25078 100644 --- a/tools/pyang_plugins/bgpyang2golang.py +++ b/tools/pyang_plugins/bgpyang2golang.py @@ -94,6 +94,7 @@ def emit_go(ctx): for mod in ctx.module_deps: if mod not in _module_excluded: emit_typedef(ctx, mod) + emit_identity(ctx, mod) for struct in ctx.golang_struct_def: struct_name = struct.uniq_name @@ -154,7 +155,7 @@ def emit_class_def(ctx, yang_statement, struct_name, prefix): # case identityref if type_name == 'identityref': - emit_type_name = 'string' + emit_type_name = convert_to_golang(type_obj.search_one('base').arg.split(':')[-1]) # case leafref elif type_name == 'leafref': @@ -163,6 +164,8 @@ def emit_class_def(ctx, yang_statement, struct_name, prefix): print >> o, ' //%s:%s\'s original type is %s' \ % (child_prefix, container_or_list_name, t.arg) emit_type_name = translate_type(t.arg) + elif is_identityref(t): + emit_type_name = convert_to_golang(t.search_one('base').arg.split(':')[-1]) else: emit_type_name = t.arg @@ -203,6 +206,9 @@ def emit_class_def(ctx, yang_statement, struct_name, prefix): t = type_obj.i_type_spec.i_target_node.search_one('type') emit_type_name = '[]'+t.arg + elif type_name == 'identityref': + emit_type_name = '[]'+convert_to_golang(type_obj.search_one('base').arg.split(':')[-1]) + # case translation required elif is_translation_required(type_obj): print >> o, ' // original type is list of %s' % (type_obj.arg) @@ -372,6 +378,15 @@ def visit_identity(ctx, module): name = stmts.arg stmts.golang_name = convert_to_golang(name) child_map[name] = stmts + + base = stmts.search_one('base') + if base: + elems = base.arg.split(':') + if len(elems) > 1: + ctx.golang_identity_map[elems[0]][elems[1]].substmts.append(stmts) + else: + child_map[base.arg].substmts.append(stmts) + ctx.golang_identity_map[prefix] = child_map @@ -398,6 +413,68 @@ def lookup(basemap, default_prefix, key): return key +def emit_enum(prefix, name, stmt, substmts): + type_name_org = name + type_name = stmt.golang_name + o = StringIO.StringIO() + + print >> o, '// typedef for identity %s:%s' % (prefix, type_name_org) + print >> o, 'type %s string' % (type_name) + + const_prefix = convert_const_prefix(type_name_org) + print >> o, 'const (' + m = {} + for sub in substmts: + enum_name = '%s_%s' % (const_prefix, convert_const_prefix(sub.arg)) + m[sub.arg.lower()] = enum_name + print >> o, ' %s %s = "%s"' % (enum_name, type_name, sub.arg.lower()) + print >> o, ')\n' + + print >> o, 'var %sToIntMap = map[%s]int {' % (type_name, type_name) + for i, sub in enumerate(substmts): + enum_name = '%s_%s' % (const_prefix, convert_const_prefix(sub.arg)) + print >> o, ' %s: %d,' % (enum_name, i) + print >> o, '}\n' + + print >> o, 'func (v %s) ToInt() int {' % (type_name) + print >> o, 'i, ok := %sToIntMap[v]' % (type_name) + print >> o, 'if !ok {' + print >> o, 'return -1' + print >> o, '}' + print >> o, 'return i' + print >> o, '}' + + print >> o, 'var IntTo%sMap = map[int]%s {' % (type_name, type_name) + for i, sub in enumerate(substmts): + enum_name = '%s_%s' % (const_prefix, convert_const_prefix(sub.arg)) + print >> o, ' %d: %s,' % (i, enum_name) + print >> o, '}\n' + + print >> o, 'func (v %s) Validate() error {' % (type_name) + print >> o, 'if _, ok := %sToIntMap[v]; !ok {' % (type_name) + print >> o, 'return fmt.Errorf("invalid %s: %%s", v)' % (type_name) + print >> o, '}' + print >> o, 'return nil' + print >> o, '}\n' + + if stmt.search_one('default'): + default = stmt.search_one('default') + print >> o, 'func (v %s) Default() %s {' % (type_name, type_name) + print >> o, 'return %s' % m[default.arg.lower()] + print >> o, '}\n' + + print >> o, 'func (v %s) DefaultAsNeeded() %s {' % (type_name, type_name) + print >> o, ' if string(v) == "" {' + print >> o, ' return v.Default()' + print >> o, '}' + print >> o, ' return v' + print >> o, '}' + + + + print o.getvalue() + + def emit_typedef(ctx, module): prefix = module.i_prefix t_map = ctx.golang_typedef_map[prefix] @@ -424,55 +501,7 @@ def emit_typedef(ctx, module): o = StringIO.StringIO() if t.arg == 'enumeration': - print >> o, '// typedef for typedef %s:%s'\ - % (prefix, type_name_org) - print >> o, 'type %s string' % (type_name) - - const_prefix = convert_const_prefix(type_name_org) - print >> o, 'const (' - m = {} - for sub in t.substmts: - enum_name = '%s_%s' % (const_prefix, convert_const_prefix(sub.arg)) - m[sub.arg.lower()] = enum_name - print >> o, ' %s %s = "%s"' % (enum_name, type_name, sub.arg.lower()) - print >> o, ')\n' - - print >> o, 'func (v %s) ToInt() int {' % (type_name) - print >> o, 'for i, vv := range []string{%s} {' % (",".join('"%s"' % s.arg.lower() for s in t.substmts)) - print >> o, 'if string(v) == vv {return i}' - print >> o, '}' - print >> o, 'return -1' - print >> o, '}\n' - - print >> o, 'func (v %s) FromInt(i int) %s {' % (type_name, type_name) - print >> o, 'for j, vv := range []string{%s} {' % (",".join('"%s"' % s.arg.lower() for s in t.substmts)) - print >> o, 'if i == j {return %s(vv)}' % (type_name) - print >> o, '}' - print >> o, 'return %s("")' % (type_name) - print >> o, '}\n' - - print >> o, 'func (v %s) Validate() error {' % (type_name) - print >> o, 'if v.ToInt() < 0 {' - print >> o, 'return fmt.Errorf("invalid %s: %%s", v)' % (type_name) - print >> o, '}' - print >> o, 'return nil' - print >> o, '}\n' - - if stmt.search_one('default'): - default = stmt.search_one('default') - print >> o, 'func (v %s) Default() %s {' % (type_name, type_name) - print >> o, 'return %s' % m[default.arg.lower()] - print >> o, '}\n' - - print >> o, 'func (v %s) DefaultAsNeeded() %s {' % (type_name, type_name) - print >> o, ' if string(v) == "" {' - print >> o, ' return v.Default()' - print >> o, '}' - print >> o, ' return v' - print >> o, '}' - - - + emit_enum(prefix, type_name_org, stmt, t.substmts) elif t.arg == 'union': print >> o, '// typedef for typedef %s:%s'\ % (prefix, type_name_org) @@ -497,29 +526,18 @@ def emit_identity(ctx, module): prefix = module.i_prefix i_map = ctx.golang_identity_map[prefix] for name, stmt in i_map.items(): - type_name_org = name - type_name = stmt.golang_name - base = stmt.search_one('base') - o = StringIO.StringIO() - - print >> o, '// typedef for identity %s:%s' % (prefix, type_name_org) - print >> o, 'type %s struct {' % (type_name) - if base is not None: - base_obj = lookup_identity(ctx, prefix, base.arg) - print >> o, ' // base_type -> %s' % (base.arg) - print >> o, ' %s' % (base_obj.golang_name) - - print >> o, '}' - print o.getvalue() - + enums = stmt.search('identity') + if len(enums) > 0: + emit_enum(prefix, name, stmt, enums) def is_reference(s): return s.arg in ['leafref', 'identityref'] - def is_leafref(s): return s.arg in ['leafref'] +def is_identityref(s): + return s.arg in ['identityref'] def is_leaf(s): return s.keyword in ['leaf'] @@ -563,7 +581,6 @@ _type_translation_map = { 'inet:ipv4-address': 'string', 'inet:as-number': 'uint32', 'bgp-set-community-option-type': 'string', - 'identityref' : 'string', 'inet:port-number': 'uint16', 'yang:timeticks': 'int64', 'ptypes:install-protocol-type': 'string', diff --git a/tools/pyang_plugins/gobgp.yang b/tools/pyang_plugins/gobgp.yang index 1cf34800..29e3342d 100644 --- a/tools/pyang_plugins/gobgp.yang +++ b/tools/pyang_plugins/gobgp.yang @@ -9,6 +9,7 @@ module gobgp { // import some basic types import openconfig-bgp { prefix bgp; } + import openconfig-bgp-types { prefix bgp-types; } import openconfig-routing-policy {prefix rpol; } import openconfig-policy-types {prefix ptypes; } import openconfig-bgp-policy {prefix bgp-pol; } @@ -49,6 +50,74 @@ module gobgp { } } + identity eq { + base ptypes:attribute-comparison; + } + + identity ge { + base ptypes:attribute-comparison; + } + + identity le { + base ptypes:attribute-comparison; + } + + identity IPV4-MULTICAST { + base bgp-types:afi-safi-type; + description + "IPv4 multicast (AFI,SAFI = 1,2)"; + reference "RFC4760"; + } + + identity IPV6-MULTICAST { + base bgp-types:afi-safi-type; + description + "IPv4 multicast (AFI,SAFI = 1,2)"; + reference "RFC4760"; + } + + identity RTC { + base bgp-types:afi-safi-type; + description + "Route target membership (AFI,SAFI = 1,132)"; + reference "RFC4684"; + } + + identity ENCAP { + base bgp-types:afi-safi-type; + description + "Encapsulation (AFI,SAFI = 1,7)"; + reference "RFC5512"; + } + + identity IPV4-FLOWSPEC { + base bgp-types:afi-safi-type; + description + "IPv4 flowspec (AFI,SAFI = 1,133)"; + reference "RFC5575"; + } + + identity L3VPN-IPV4-FLOWSPEC { + base bgp-types:afi-safi-type; + description + "L3VPN IPv4 flowspec (AFI,SAFI = 1,134)"; + reference "RFC5575"; + } + + identity IPV6-FLOWSPEC { + base bgp-types:afi-safi-type; + description + "IPv6 flowspec (AFI,SAFI = 1,133)"; + reference "RFC5575"; + } + + identity L3VPN-IPV6-FLOWSPEC { + base bgp-types:afi-safi-type; + description + "L3VPN IPv6 flowspec (AFI,SAFI = 1,134)"; + reference "RFC5575"; + } + grouping gobgp-message-counter { description "Counters for all BGPMessage types"; |