Annotation of embedaddon/bird/proto/ospf/config.Y, revision 1.1

1.1     ! misho       1: /*
        !             2:  *     BIRD -- OSPF Configuration
        !             3:  *
        !             4:  *     (c) 1999--2004 Ondrej Filip <feela@network.cz>
        !             5:  *
        !             6:  *     Can be freely distributed and used under the terms of the GNU GPL.
        !             7:  */
        !             8: 
        !             9: CF_HDR
        !            10: 
        !            11: #include "proto/ospf/ospf.h"
        !            12: 
        !            13: CF_DEFINES
        !            14: 
        !            15: #define OSPF_CFG ((struct ospf_config *) this_proto)
        !            16: #define OSPF_PATT ((struct ospf_iface_patt *) this_ipatt)
        !            17: 
        !            18: static struct ospf_area_config *this_area;
        !            19: static struct nbma_node *this_nbma;
        !            20: static list *this_nets;
        !            21: static struct area_net_config *this_pref;
        !            22: static struct ospf_stubnet_config *this_stubnet;
        !            23: 
        !            24: static inline int ospf_cfg_is_v2(void) { return OSPF_CFG->ospf2; }
        !            25: static inline int ospf_cfg_is_v3(void) { return ! OSPF_CFG->ospf2; }
        !            26: 
        !            27: static void
        !            28: ospf_iface_finish(void)
        !            29: {
        !            30:   struct ospf_iface_patt *ip = OSPF_PATT;
        !            31: 
        !            32:   if (ip->deadint == 0)
        !            33:     ip->deadint = ip->deadc * ip->helloint;
        !            34: 
        !            35:   if (ip->waitint == 0)
        !            36:     ip->waitint = ip->deadc * ip->helloint;
        !            37: 
        !            38:   ip->passwords = get_passwords();
        !            39: 
        !            40:   if ((ip->autype == OSPF_AUTH_CRYPT) && (ip->helloint < 5))
        !            41:     log(L_WARN "Hello or poll interval less that 5 makes cryptographic authenication prone to replay attacks");
        !            42: 
        !            43:   if ((ip->autype == OSPF_AUTH_NONE) && (ip->passwords != NULL))
        !            44:     log(L_WARN "Password option without authentication option does not make sense");
        !            45: 
        !            46:   if (ip->passwords)
        !            47:   {
        !            48:     struct password_item *pass;
        !            49:     WALK_LIST(pass, *ip->passwords)
        !            50:     {
        !            51:       if (pass->alg && (ip->autype != OSPF_AUTH_CRYPT))
        !            52:        cf_error("Password algorithm option requires cryptographic authentication");
        !            53: 
        !            54:       /* Set default OSPF crypto algorithms */
        !            55:       if (!pass->alg && (ip->autype == OSPF_AUTH_CRYPT))
        !            56:        pass->alg = ospf_cfg_is_v2() ? ALG_MD5 : ALG_HMAC_SHA256;
        !            57:     }
        !            58:   }
        !            59: }
        !            60: 
        !            61: static void
        !            62: ospf_area_finish(void)
        !            63: {
        !            64:   if ((this_area->areaid == 0) && (this_area->type != OPT_E))
        !            65:     cf_error("Backbone area cannot be stub/NSSA");
        !            66: 
        !            67:   if (this_area->summary && (this_area->type == OPT_E))
        !            68:     cf_error("Only stub/NSSA areas can use summary propagation");
        !            69: 
        !            70:   if (this_area->default_nssa && ((this_area->type != OPT_N) || ! this_area->summary))
        !            71:     cf_error("Only NSSA areas with summary propagation can use NSSA default route");
        !            72: 
        !            73:   if ((this_area->default_cost & LSA_EXT3_EBIT) && ! this_area->default_nssa)
        !            74:     cf_error("Only NSSA default route can use type 2 metric");
        !            75: }
        !            76: 
        !            77: static void
        !            78: ospf_proto_finish(void)
        !            79: {
        !            80:   struct ospf_config *cf = OSPF_CFG;
        !            81: 
        !            82:   if (EMPTY_LIST(cf->area_list))
        !            83:     cf_error( "No configured areas in OSPF");
        !            84: 
        !            85:   int areano = 0;
        !            86:   int backbone = 0;
        !            87:   int nssa = 0;
        !            88:   struct ospf_area_config *ac;
        !            89:   WALK_LIST(ac, cf->area_list)
        !            90:   {
        !            91:     areano++;
        !            92:     if (ac->areaid == 0)
        !            93:       backbone = 1;
        !            94:     if (ac->type == OPT_N)
        !            95:       nssa = 1;
        !            96:   }
        !            97: 
        !            98:   cf->abr = areano > 1;
        !            99: 
        !           100:   /* Route export or NSSA translation (RFC 3101 3.1) */
        !           101:   cf->asbr = (this_proto->out_filter != FILTER_REJECT) || (nssa && cf->abr);
        !           102: 
        !           103:   if (cf->abr && !backbone)
        !           104:   {
        !           105:     struct ospf_area_config *ac = cfg_allocz(sizeof(struct ospf_area_config));
        !           106:     ac->type = OPT_E; /* Backbone is non-stub */
        !           107:     add_head(&cf->area_list, NODE ac);
        !           108:     init_list(&ac->patt_list);
        !           109:     init_list(&ac->net_list);
        !           110:     init_list(&ac->enet_list);
        !           111:     init_list(&ac->stubnet_list);
        !           112:   }
        !           113: 
        !           114:   if (!cf->abr && !EMPTY_LIST(cf->vlink_list))
        !           115:     cf_error("Vlinks cannot be used on single area router");
        !           116: 
        !           117:   if (cf->asbr && (areano == 1) && (this_area->type == 0))
        !           118:     cf_error("ASBR must be in non-stub area");
        !           119: }
        !           120: 
        !           121: static inline void
        !           122: ospf_check_defcost(int cost)
        !           123: {
        !           124:   if ((cost <= 0) || (cost >= LSINFINITY))
        !           125:    cf_error("Default cost must be in range 1-%d", LSINFINITY-1);
        !           126: }
        !           127: 
        !           128: static inline void
        !           129: ospf_check_auth(void)
        !           130: {
        !           131:   if (ospf_cfg_is_v3())
        !           132:     cf_error("Authentication not supported in OSPFv3");
        !           133: }
        !           134: 
        !           135: 
        !           136: CF_DECLS
        !           137: 
        !           138: CF_KEYWORDS(OSPF, AREA, OSPF_METRIC1, OSPF_METRIC2, OSPF_TAG, OSPF_ROUTER_ID)
        !           139: CF_KEYWORDS(NEIGHBORS, RFC1583COMPAT, STUB, TICK, COST, COST2, RETRANSMIT)
        !           140: CF_KEYWORDS(HELLO, TRANSMIT, PRIORITY, DEAD, TYPE, BROADCAST, BCAST, DEFAULT)
        !           141: CF_KEYWORDS(NONBROADCAST, NBMA, POINTOPOINT, PTP, POINTOMULTIPOINT, PTMP)
        !           142: CF_KEYWORDS(NONE, SIMPLE, AUTHENTICATION, STRICT, CRYPTOGRAPHIC, TTL, SECURITY)
        !           143: CF_KEYWORDS(ELIGIBLE, POLL, NETWORKS, HIDDEN, VIRTUAL, CHECK, LINK, ONLY, BFD)
        !           144: CF_KEYWORDS(RX, BUFFER, LARGE, NORMAL, STUBNET, HIDDEN, SUMMARY, TAG, EXTERNAL)
        !           145: CF_KEYWORDS(WAIT, DELAY, LSADB, ECMP, LIMIT, WEIGHT, NSSA, TRANSLATOR, STABILITY)
        !           146: CF_KEYWORDS(GLOBAL, LSID, ROUTER, SELF, INSTANCE, REAL, NETMASK, TX, PRIORITY, LENGTH)
        !           147: CF_KEYWORDS(SECONDARY, MERGE, LSA, SUPPRESSION)
        !           148: 
        !           149: %type <t> opttext
        !           150: %type <ld> lsadb_args
        !           151: %type <i> nbma_eligible
        !           152: 
        !           153: CF_GRAMMAR
        !           154: 
        !           155: CF_ADDTO(proto, ospf_proto '}' { ospf_proto_finish(); } )
        !           156: 
        !           157: ospf_proto_start: proto_start OSPF {
        !           158:      this_proto = proto_config_new(&proto_ospf, $1);
        !           159:      init_list(&OSPF_CFG->area_list);
        !           160:      init_list(&OSPF_CFG->vlink_list);
        !           161:      OSPF_CFG->tick = OSPF_DEFAULT_TICK;
        !           162:      OSPF_CFG->ospf2 = OSPF_IS_V2;
        !           163:   }
        !           164:  ;
        !           165: 
        !           166: ospf_proto:
        !           167:    ospf_proto_start proto_name '{'
        !           168:  | ospf_proto ospf_proto_item ';'
        !           169:  ;
        !           170: 
        !           171: ospf_proto_item:
        !           172:    proto_item
        !           173:  | RFC1583COMPAT bool { OSPF_CFG->rfc1583 = $2; }
        !           174:  | STUB ROUTER bool { OSPF_CFG->stub_router = $3; }
        !           175:  | ECMP bool { OSPF_CFG->ecmp = $2 ? OSPF_DEFAULT_ECMP_LIMIT : 0; }
        !           176:  | ECMP bool LIMIT expr { OSPF_CFG->ecmp = $2 ? $4 : 0; if ($4 < 0) cf_error("ECMP limit cannot be negative"); }
        !           177:  | MERGE EXTERNAL bool { OSPF_CFG->merge_external = $3; }
        !           178:  | TICK expr { OSPF_CFG->tick = $2; if($2<=0) cf_error("Tick must be greater than zero"); }
        !           179:  | INSTANCE ID expr { OSPF_CFG->instance_id = $3; if (($3<0) || ($3>255)) cf_error("Instance ID must be in range 0-255"); }
        !           180:  | ospf_area
        !           181:  ;
        !           182: 
        !           183: ospf_area_start: AREA idval {
        !           184:   this_area = cfg_allocz(sizeof(struct ospf_area_config));
        !           185:   add_tail(&OSPF_CFG->area_list, NODE this_area);
        !           186:   this_area->areaid = $2;
        !           187:   this_area->default_cost = OSPF_DEFAULT_STUB_COST;
        !           188:   this_area->type = OPT_E;
        !           189:   this_area->transint = OSPF_DEFAULT_TRANSINT;
        !           190: 
        !           191:   init_list(&this_area->patt_list);
        !           192:   init_list(&this_area->net_list);
        !           193:   init_list(&this_area->enet_list);
        !           194:   init_list(&this_area->stubnet_list);
        !           195:  }
        !           196:  ;
        !           197: 
        !           198: ospf_area: ospf_area_start '{' ospf_area_opts '}' { ospf_area_finish(); }
        !           199:  ;
        !           200: 
        !           201: ospf_area_opts:
        !           202:    /* empty */
        !           203:  | ospf_area_opts ospf_area_item ';'
        !           204:  ;
        !           205: 
        !           206: ospf_area_item:
        !           207:    STUB bool { this_area->type = $2 ? 0 : OPT_E; /* We should remove the option */ }
        !           208:  | NSSA { this_area->type = OPT_N; }
        !           209:  | SUMMARY bool { this_area->summary = $2; }
        !           210:  | DEFAULT NSSA bool { this_area->default_nssa = $3; }
        !           211:  | DEFAULT COST expr { this_area->default_cost = $3; ospf_check_defcost($3); }
        !           212:  | DEFAULT COST2 expr { this_area->default_cost = $3 | LSA_EXT3_EBIT; ospf_check_defcost($3); }
        !           213:  | STUB COST expr { this_area->default_cost = $3; ospf_check_defcost($3); }
        !           214:  | TRANSLATOR bool { this_area->translator = $2; }
        !           215:  | TRANSLATOR STABILITY expr { this_area->transint = $3; }
        !           216:  | NETWORKS { this_nets = &this_area->net_list; } '{' pref_list '}'
        !           217:  | EXTERNAL { this_nets = &this_area->enet_list; } '{' pref_list '}'
        !           218:  | STUBNET ospf_stubnet
        !           219:  | INTERFACE ospf_iface
        !           220:  | ospf_vlink
        !           221:  ;
        !           222: 
        !           223: ospf_stubnet:
        !           224:    ospf_stubnet_start '{' ospf_stubnet_opts '}'
        !           225:  | ospf_stubnet_start
        !           226:  ;
        !           227: 
        !           228: ospf_stubnet_start:
        !           229:    prefix {
        !           230:      this_stubnet = cfg_allocz(sizeof(struct ospf_stubnet_config));
        !           231:      add_tail(&this_area->stubnet_list, NODE this_stubnet);
        !           232:      this_stubnet->px = $1;
        !           233:      this_stubnet->cost = COST_D;
        !           234:    }
        !           235:  ;
        !           236: 
        !           237: ospf_stubnet_opts:
        !           238:    /* empty */
        !           239:  | ospf_stubnet_opts ospf_stubnet_item ';'
        !           240:  ;
        !           241: 
        !           242: ospf_stubnet_item:
        !           243:    HIDDEN bool { this_stubnet->hidden = $2; }
        !           244:  | SUMMARY bool { this_stubnet->summary = $2; }
        !           245:  | COST expr { this_stubnet->cost = $2; }
        !           246:  ;
        !           247: 
        !           248: ospf_vlink:
        !           249:    ospf_vlink_start ospf_instance_id '{' ospf_vlink_opts '}' { ospf_iface_finish(); }
        !           250:  | ospf_vlink_start ospf_instance_id { ospf_iface_finish(); }
        !           251:  ;
        !           252: 
        !           253: ospf_vlink_opts:
        !           254:    /* empty */
        !           255:  | ospf_vlink_opts ospf_vlink_item ';'
        !           256:  ;
        !           257: 
        !           258: ospf_vlink_item:
        !           259:  | HELLO expr { OSPF_PATT->helloint = $2 ; if (($2<=0) || ($2>65535)) cf_error("Hello interval must be in range 1-65535"); }
        !           260:  | RETRANSMIT expr { OSPF_PATT->rxmtint = $2 ; if ($2<=1) cf_error("Retransmit int must be greater than one"); }
        !           261:  | TRANSMIT DELAY expr { OSPF_PATT->inftransdelay = $3 ; if (($3<=0) || ($3>65535)) cf_error("Transmit delay must be in range 1-65535"); }
        !           262:  | WAIT expr { OSPF_PATT->waitint = $2 ; if ($2<=1) cf_error("Wait interval must be greater than one"); }
        !           263:  | DEAD expr { OSPF_PATT->deadint = $2 ; if ($2<=1) cf_error("Dead interval must be greater than one"); }
        !           264:  | DEAD COUNT expr { OSPF_PATT->deadc = $3 ; if ($3<=1) cf_error("Dead count must be greater than one"); }
        !           265:  | AUTHENTICATION NONE { OSPF_PATT->autype = OSPF_AUTH_NONE;  }
        !           266:  | AUTHENTICATION SIMPLE { OSPF_PATT->autype = OSPF_AUTH_SIMPLE; ospf_check_auth(); }
        !           267:  | AUTHENTICATION CRYPTOGRAPHIC { OSPF_PATT->autype = OSPF_AUTH_CRYPT; ospf_check_auth(); }
        !           268:  | password_list { ospf_check_auth(); }
        !           269:  ;
        !           270: 
        !           271: ospf_vlink_start: VIRTUAL LINK idval
        !           272:  {
        !           273:   if (this_area->areaid == 0) cf_error("Virtual link cannot be in backbone");
        !           274:   this_ipatt = cfg_allocz(sizeof(struct ospf_iface_patt));
        !           275:   add_tail(&OSPF_CFG->vlink_list, NODE this_ipatt);
        !           276:   init_list(&this_ipatt->ipn_list);
        !           277:   OSPF_PATT->voa = this_area->areaid;
        !           278:   OSPF_PATT->vid = $3;
        !           279:   OSPF_PATT->helloint = HELLOINT_D;
        !           280:   OSPF_PATT->rxmtint = RXMTINT_D;
        !           281:   OSPF_PATT->inftransdelay = INFTRANSDELAY_D;
        !           282:   OSPF_PATT->deadc = DEADC_D;
        !           283:   OSPF_PATT->type = OSPF_IT_VLINK;
        !           284:   OSPF_PATT->instance_id = OSPF_CFG->instance_id;
        !           285:   init_list(&OSPF_PATT->nbma_list);
        !           286:   reset_passwords();
        !           287:  }
        !           288: ;
        !           289: 
        !           290: ospf_iface_item:
        !           291:    COST expr { OSPF_PATT->cost = $2 ; if (($2<=0) || ($2>65535)) cf_error("Cost must be in range 1-65535"); }
        !           292:  | HELLO expr { OSPF_PATT->helloint = $2 ; if (($2<=0) || ($2>65535)) cf_error("Hello interval must be in range 1-65535"); }
        !           293:  | POLL expr { OSPF_PATT->pollint = $2 ; if ($2<=0) cf_error("Poll int must be greater than zero"); }
        !           294:  | RETRANSMIT expr { OSPF_PATT->rxmtint = $2 ; if ($2<=1) cf_error("Retransmit int must be greater than one"); }
        !           295:  | WAIT expr { OSPF_PATT->waitint = $2 ; if ($2<=1) cf_error("Wait interval must be greater than one"); }
        !           296:  | DEAD expr { OSPF_PATT->deadint = $2 ; if ($2<=1) cf_error("Dead interval must be greater than one"); }
        !           297:  | DEAD COUNT expr { OSPF_PATT->deadc = $3 ; if ($3<=1) cf_error("Dead count must be greater than one"); }
        !           298:  | TYPE BROADCAST { OSPF_PATT->type = OSPF_IT_BCAST ; }
        !           299:  | TYPE BCAST { OSPF_PATT->type = OSPF_IT_BCAST ; }
        !           300:  | TYPE NONBROADCAST { OSPF_PATT->type = OSPF_IT_NBMA ; }
        !           301:  | TYPE NBMA { OSPF_PATT->type = OSPF_IT_NBMA ; }
        !           302:  | TYPE POINTOPOINT { OSPF_PATT->type = OSPF_IT_PTP ; }
        !           303:  | TYPE PTP { OSPF_PATT->type = OSPF_IT_PTP ; }
        !           304:  | TYPE POINTOMULTIPOINT { OSPF_PATT->type = OSPF_IT_PTMP ; }
        !           305:  | TYPE PTMP { OSPF_PATT->type = OSPF_IT_PTMP ; }
        !           306:  | REAL BROADCAST bool { OSPF_PATT->real_bcast = $3; if (!ospf_cfg_is_v2()) cf_error("Real broadcast option requires OSPFv2"); }
        !           307:  | PTP NETMASK bool { OSPF_PATT->ptp_netmask = $3; if (!ospf_cfg_is_v2()) cf_error("PtP netmask option requires OSPFv2"); }
        !           308:  | TRANSMIT DELAY expr { OSPF_PATT->inftransdelay = $3 ; if (($3<=0) || ($3>65535)) cf_error("Transmit delay must be in range 1-65535"); }
        !           309:  | PRIORITY expr { OSPF_PATT->priority = $2 ; if (($2<0) || ($2>255)) cf_error("Priority must be in range 0-255"); }
        !           310:  | STRICT NONBROADCAST bool { OSPF_PATT->strictnbma = $3 ; }
        !           311:  | STUB bool { OSPF_PATT->stub = $2 ; }
        !           312:  | CHECK LINK bool { OSPF_PATT->check_link = $3; }
        !           313:  | ECMP WEIGHT expr { OSPF_PATT->ecmp_weight = $3 - 1; if (($3<1) || ($3>256)) cf_error("ECMP weight must be in range 1-256"); }
        !           314:  | LINK LSA SUPPRESSION bool { OSPF_PATT->link_lsa_suppression = $4; if (!ospf_cfg_is_v3()) cf_error("Link LSA suppression option requires OSPFv3"); }
        !           315:  | NEIGHBORS '{' nbma_list '}'
        !           316:  | AUTHENTICATION NONE { OSPF_PATT->autype = OSPF_AUTH_NONE; }
        !           317:  | AUTHENTICATION SIMPLE { OSPF_PATT->autype = OSPF_AUTH_SIMPLE; ospf_check_auth(); }
        !           318:  | AUTHENTICATION CRYPTOGRAPHIC { OSPF_PATT->autype = OSPF_AUTH_CRYPT; ospf_check_auth(); }
        !           319:  | RX BUFFER NORMAL { OSPF_PATT->rx_buffer = 0; }
        !           320:  | RX BUFFER LARGE { OSPF_PATT->rx_buffer = OSPF_MAX_PKT_SIZE; }
        !           321:  | RX BUFFER expr { OSPF_PATT->rx_buffer = $3; if (($3 < OSPF_MIN_PKT_SIZE) || ($3 > OSPF_MAX_PKT_SIZE)) cf_error("Buffer size must be in range 256-65535"); }
        !           322:  | TX tos { OSPF_PATT->tx_tos = $2; }
        !           323:  | TX PRIORITY expr { OSPF_PATT->tx_priority = $3; }
        !           324:  | TX LENGTH expr { OSPF_PATT->tx_length = $3; if (($3 < OSPF_MIN_PKT_SIZE) || ($3 > OSPF_MAX_PKT_SIZE)) cf_error("TX length must be in range 256-65535"); }
        !           325:  | TTL SECURITY bool { OSPF_PATT->ttl_security = $3; }
        !           326:  | TTL SECURITY TX ONLY { OSPF_PATT->ttl_security = 2; }
        !           327:  | BFD bool { OSPF_PATT->bfd = $2; cf_check_bfd($2); }
        !           328:  | SECONDARY bool { OSPF_PATT->bsd_secondary = $2; }
        !           329:  | password_list { ospf_check_auth(); }
        !           330:  ;
        !           331: 
        !           332: pref_list:
        !           333:  /* empty */
        !           334:  | pref_list pref_item
        !           335:  ;
        !           336: 
        !           337: pref_item: pref_base pref_opt ';' ;
        !           338: 
        !           339: pref_base: prefix
        !           340:  {
        !           341:    this_pref = cfg_allocz(sizeof(struct area_net_config));
        !           342:    add_tail(this_nets, NODE this_pref);
        !           343:    this_pref->px.addr = $1.addr;
        !           344:    this_pref->px.len = $1.len;
        !           345:  }
        !           346: ;
        !           347: 
        !           348: pref_opt:
        !           349:  /* empty */
        !           350:  | HIDDEN { this_pref->hidden = 1; }
        !           351:  | TAG expr { this_pref->tag = $2; }
        !           352:  ;
        !           353: 
        !           354: nbma_list:
        !           355:  /* empty */
        !           356:  | nbma_list nbma_item
        !           357:  ;
        !           358: 
        !           359: nbma_eligible:
        !           360:  /* empty */ { $$ = 0; }
        !           361:  | ELIGIBLE { $$ = 1; }
        !           362:  ;
        !           363: 
        !           364: nbma_item: ipa nbma_eligible ';'
        !           365:  {
        !           366:    this_nbma = cfg_allocz(sizeof(struct nbma_node));
        !           367:    add_tail(&OSPF_PATT->nbma_list, NODE this_nbma);
        !           368:    this_nbma->ip=$1;
        !           369:    this_nbma->eligible=$2;
        !           370:  }
        !           371: ;
        !           372: 
        !           373: ospf_iface_start:
        !           374:  {
        !           375:   this_ipatt = cfg_allocz(sizeof(struct ospf_iface_patt));
        !           376:   add_tail(&this_area->patt_list, NODE this_ipatt);
        !           377:   init_list(&this_ipatt->ipn_list);
        !           378:   OSPF_PATT->cost = COST_D;
        !           379:   OSPF_PATT->helloint = HELLOINT_D;
        !           380:   OSPF_PATT->pollint = POLLINT_D;
        !           381:   OSPF_PATT->rxmtint = RXMTINT_D;
        !           382:   OSPF_PATT->inftransdelay = INFTRANSDELAY_D;
        !           383:   OSPF_PATT->priority = PRIORITY_D;
        !           384:   OSPF_PATT->deadc = DEADC_D;
        !           385:   OSPF_PATT->type = OSPF_IT_UNDEF;
        !           386:   OSPF_PATT->instance_id = OSPF_CFG->instance_id;
        !           387:   init_list(&OSPF_PATT->nbma_list);
        !           388:   OSPF_PATT->ptp_netmask = 2; /* not specified */
        !           389:   OSPF_PATT->tx_tos = IP_PREC_INTERNET_CONTROL;
        !           390:   OSPF_PATT->tx_priority = sk_priority_control;
        !           391:   reset_passwords();
        !           392:  }
        !           393: ;
        !           394: 
        !           395: ospf_instance_id:
        !           396:    /* empty */
        !           397:  | INSTANCE expr { OSPF_PATT->instance_id = $2; if (($2<0) || ($2>255)) cf_error("Instance ID must be in range 0-255"); }
        !           398:  ;
        !           399: 
        !           400: ospf_iface_patt_list:
        !           401:    iface_patt_list { if (ospf_cfg_is_v3()) iface_patt_check(); } ospf_instance_id
        !           402:  ;
        !           403: 
        !           404: ospf_iface_opts:
        !           405:    /* empty */
        !           406:  | ospf_iface_opts ospf_iface_item ';'
        !           407:  ;
        !           408: 
        !           409: ospf_iface_opt_list:
        !           410:    /* empty */
        !           411:  | '{' ospf_iface_opts '}'
        !           412:  ;
        !           413: 
        !           414: ospf_iface:
        !           415:   ospf_iface_start ospf_iface_patt_list ospf_iface_opt_list { ospf_iface_finish(); }
        !           416:  ;
        !           417: 
        !           418: opttext:
        !           419:     TEXT
        !           420:  | /* empty */ { $$ = NULL; }
        !           421:  ;
        !           422: 
        !           423: CF_ADDTO(dynamic_attr, OSPF_METRIC1 { $$ = f_new_dynamic_attr(EAF_TYPE_INT | EAF_TEMP, T_INT, EA_OSPF_METRIC1); })
        !           424: CF_ADDTO(dynamic_attr, OSPF_METRIC2 { $$ = f_new_dynamic_attr(EAF_TYPE_INT | EAF_TEMP, T_INT, EA_OSPF_METRIC2); })
        !           425: CF_ADDTO(dynamic_attr, OSPF_TAG { $$ = f_new_dynamic_attr(EAF_TYPE_INT | EAF_TEMP, T_INT, EA_OSPF_TAG); })
        !           426: CF_ADDTO(dynamic_attr, OSPF_ROUTER_ID { $$ = f_new_dynamic_attr(EAF_TYPE_ROUTER_ID | EAF_TEMP, T_QUAD, EA_OSPF_ROUTER_ID); })
        !           427: 
        !           428: CF_CLI_HELP(SHOW OSPF, ..., [[Show information about OSPF protocol]]);
        !           429: CF_CLI(SHOW OSPF, optsym, [<name>], [[Show information about OSPF protocol XXX]])
        !           430: { ospf_sh(proto_get_named($3, &proto_ospf)); };
        !           431: 
        !           432: CF_CLI(SHOW OSPF NEIGHBORS, optsym opttext, [<name>] [\"<interface>\"], [[Show information about OSPF neighbors]])
        !           433: { ospf_sh_neigh(proto_get_named($4, &proto_ospf), $5); };
        !           434: 
        !           435: CF_CLI(SHOW OSPF INTERFACE, optsym opttext, [<name>] [\"<interface>\"], [[Show information about interface]])
        !           436: { ospf_sh_iface(proto_get_named($4, &proto_ospf), $5); };
        !           437: 
        !           438: CF_CLI_HELP(SHOW OSPF TOPOLOGY, [all] [<name>], [[Show information about OSPF network topology]])
        !           439: 
        !           440: CF_CLI(SHOW OSPF TOPOLOGY, optsym opttext, [<name>], [[Show information about reachable OSPF network topology]])
        !           441: { ospf_sh_state(proto_get_named($4, &proto_ospf), 0, 1); };
        !           442: 
        !           443: CF_CLI(SHOW OSPF TOPOLOGY ALL, optsym opttext, [<name>], [[Show information about all OSPF network topology]])
        !           444: { ospf_sh_state(proto_get_named($5, &proto_ospf), 0, 0); };
        !           445: 
        !           446: CF_CLI_HELP(SHOW OSPF STATE, [all] [<name>], [[Show information about OSPF network state]])
        !           447: 
        !           448: CF_CLI(SHOW OSPF STATE, optsym opttext, [<name>], [[Show information about reachable OSPF network state]])
        !           449: { ospf_sh_state(proto_get_named($4, &proto_ospf), 1, 1); };
        !           450: 
        !           451: CF_CLI(SHOW OSPF STATE ALL, optsym opttext, [<name>], [[Show information about all OSPF network state]])
        !           452: { ospf_sh_state(proto_get_named($5, &proto_ospf), 1, 0); };
        !           453: 
        !           454: CF_CLI_HELP(SHOW OSPF LSADB, ..., [[Show content of OSPF LSA database]]);
        !           455: CF_CLI(SHOW OSPF LSADB, lsadb_args, [global | area <id> | link] [type <num>] [lsid <id>] [self | router <id>] [<proto>], [[Show content of OSPF LSA database]])
        !           456: { ospf_sh_lsadb($4); };
        !           457: 
        !           458: lsadb_args:
        !           459:    /* empty */ {
        !           460:      $$ = cfg_allocz(sizeof(struct lsadb_show_data));
        !           461:    }
        !           462:  | lsadb_args GLOBAL { $$ = $1; $$->scope = LSA_SCOPE_AS; }
        !           463:  | lsadb_args AREA idval { $$ = $1; $$->scope = LSA_SCOPE_AREA; $$->area = $3; }
        !           464:  | lsadb_args LINK { $$ = $1; $$->scope = 1; /* hack, 0 is no filter */ }
        !           465:  | lsadb_args TYPE NUM { $$ = $1; $$->type = $3; }
        !           466:  | lsadb_args LSID idval { $$ = $1; $$->lsid = $3; }
        !           467:  | lsadb_args SELF { $$ = $1; $$->router = SH_ROUTER_SELF; }
        !           468:  | lsadb_args ROUTER idval { $$ = $1; $$->router = $3; }
        !           469:  | lsadb_args SYM { $$ = $1; $$->name = $2; }
        !           470:  ;
        !           471: 
        !           472: CF_CODE
        !           473: 
        !           474: CF_END

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>