summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorISHIDA Wataru <ishida.wataru@lab.ntt.co.jp>2016-01-10 17:45:34 +0900
committerISHIDA Wataru <ishida.wataru@lab.ntt.co.jp>2016-01-10 20:03:27 +0900
commit427c665579e07edafc69351ffb4ab498a801d8b3 (patch)
treed512aaabe77f2becd562bb19ebfb935d4c7c216f
parent749b47a1183e555cdedc216065f45326a3897c21 (diff)
policy: support an action to add origin-validation ext-community
you can implement https://tools.ietf.org/html/draft-kklf-sidr-route-server-rpki-light-00 by following commands $ gobgp policy statement st0 add condition rpki valid $ gobgp policy statement st0 add action ext-community add valid $ gobgp policy statement st1 add condition rpki not-found $ gobgp policy statement st1 add action ext-community add not-found $ gobgp policy statement st2 add condition rpki invalid $ gobgp policy statement st2 add action ext-community add invalid $ gobgp policy p0 add st0 st1 st2 $ gobgp policy p0 Name p0: StatementName st0: Conditions: RPKI result: valid Actions: ExtCommunity: COMMUNITY_ADD[valid] NONE StatementName st1: Conditions: RPKI result: not-found Actions: ExtCommunity: COMMUNITY_ADD[not-found] NONE StatementName st2: Conditions: RPKI result: invalid Actions: ExtCommunity: COMMUNITY_ADD[invalid] NONE Signed-off-by: ISHIDA Wataru <ishida.wataru@lab.ntt.co.jp>
-rw-r--r--packet/bgp.go19
-rw-r--r--table/policy.go38
2 files changed, 47 insertions, 10 deletions
diff --git a/packet/bgp.go b/packet/bgp.go
index 1d7b65cc..d47e3b65 100644
--- a/packet/bgp.go
+++ b/packet/bgp.go
@@ -4559,6 +4559,25 @@ func NewFourOctetAsSpecificExtended(subtype ExtendedCommunityAttrSubType, as uin
}
func ParseExtendedCommunity(subtype ExtendedCommunityAttrSubType, com string) (ExtendedCommunityInterface, error) {
+ if subtype == EC_SUBTYPE_ORIGIN_VALIDATION {
+ var value ValidationState
+ switch com {
+ case VALIDATION_STATE_VALID.String():
+ value = VALIDATION_STATE_VALID
+ case VALIDATION_STATE_NOT_FOUND.String():
+ value = VALIDATION_STATE_NOT_FOUND
+ case VALIDATION_STATE_INVALID.String():
+ value = VALIDATION_STATE_INVALID
+ default:
+ return nil, fmt.Errorf("invalid validation state")
+ }
+ return &OpaqueExtended{
+ SubType: EC_SUBTYPE_ORIGIN_VALIDATION,
+ Value: &ValidationExtended{
+ Value: value,
+ },
+ }, nil
+ }
elems, err := parseRdAndRt(com)
if err != nil {
return nil, err
diff --git a/table/policy.go b/table/policy.go
index 675c46b2..be9ba5ad 100644
--- a/table/policy.go
+++ b/table/policy.go
@@ -843,19 +843,33 @@ func ParseCommunity(arg string) (uint32, error) {
func ParseExtCommunity(arg string) (bgp.ExtendedCommunityInterface, error) {
var subtype bgp.ExtendedCommunityAttrSubType
+ var value string
elems := strings.SplitN(arg, ":", 2)
- if len(elems) < 2 {
- return nil, fmt.Errorf("invalid ext-community format([rt|soo]:<value>)")
+
+ isValidationState := func(s string) bool {
+ s = strings.ToLower(s)
+ r := s == bgp.VALIDATION_STATE_VALID.String()
+ r = r || s == bgp.VALIDATION_STATE_NOT_FOUND.String()
+ return r || s == bgp.VALIDATION_STATE_INVALID.String()
}
- switch strings.ToLower(elems[0]) {
- case "rt":
- subtype = bgp.EC_SUBTYPE_ROUTE_TARGET
- case "soo":
- subtype = bgp.EC_SUBTYPE_ROUTE_ORIGIN
- default:
- return nil, fmt.Errorf("unknown ext-community subtype. rt, soo is supported")
+ if len(elems) < 2 && (len(elems) < 1 && !isValidationState(elems[0])) {
+ return nil, fmt.Errorf("invalid ext-community (rt|soo):<value> | valid | not-found | invalid")
+ }
+ if isValidationState(elems[0]) {
+ subtype = bgp.EC_SUBTYPE_ORIGIN_VALIDATION
+ value = elems[0]
+ } else {
+ switch strings.ToLower(elems[0]) {
+ case "rt":
+ subtype = bgp.EC_SUBTYPE_ROUTE_TARGET
+ case "soo":
+ subtype = bgp.EC_SUBTYPE_ROUTE_ORIGIN
+ default:
+ return nil, fmt.Errorf("invalid ext-community (rt|soo):<value> | valid | not-found | invalid")
+ }
+ value = elems[1]
}
- return bgp.ParseExtendedCommunity(subtype, elems[1])
+ return bgp.ParseExtendedCommunity(subtype, value)
}
func ParseCommunityRegexp(arg string) (*regexp.Regexp, error) {
@@ -942,6 +956,8 @@ func (s *ExtCommunitySet) ToApiStruct() *api.DefinedSet {
return fmt.Sprintf("rt:%s", arg)
case bgp.EC_SUBTYPE_ROUTE_ORIGIN:
return fmt.Sprintf("soo:%s", arg)
+ case bgp.EC_SUBTYPE_ORIGIN_VALIDATION:
+ return arg
default:
return fmt.Sprintf("%d:%s", s.subtypeList[idx], arg)
}
@@ -1807,6 +1823,8 @@ func (a *ExtCommunityAction) ToApiStruct() *api.CommunityAction {
return fmt.Sprintf("rt:%s", arg)
case bgp.EC_SUBTYPE_ROUTE_ORIGIN:
return fmt.Sprintf("soo:%s", arg)
+ case bgp.EC_SUBTYPE_ORIGIN_VALIDATION:
+ return arg
default:
return fmt.Sprintf("%d:%s", a.subtypeList[idx], arg)
}