Annotation of embedaddon/quagga/ospfd/ospf_abr.c, revision 1.1.1.3

1.1       misho       1: /*
                      2:  * OSPF ABR functions.
                      3:  * Copyright (C) 1999, 2000 Alex Zinin, Toshiaki Takada
                      4:  *
                      5:  * This file is part of GNU Zebra.
                      6:  *
                      7:  * GNU Zebra is free software; you can redistribute it and/or modify it
                      8:  * under the terms of the GNU General Public License as published by the
                      9:  * Free Software Foundation; either version 2, or (at your option) any
                     10:  * later version.
                     11:  * 
                     12:  * GNU Zebra is distributed in the hope that it will be useful, but
                     13:  * WITHOUT ANY WARRANTY; without even the implied warranty of
                     14:  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
                     15:  * General Public License for more details.
                     16:  * 
                     17:  * You should have received a copy of the GNU General Public License
                     18:  * along with GNU Zebra; see the file COPYING.  If not, write to the Free
                     19:  * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
                     20:  * 02111-1307, USA.
                     21:  */
                     22: 
                     23: 
                     24: #include <zebra.h>
                     25: 
                     26: #include "thread.h"
                     27: #include "memory.h"
                     28: #include "linklist.h"
                     29: #include "prefix.h"
                     30: #include "if.h"
                     31: #include "table.h"
                     32: #include "vty.h"
                     33: #include "filter.h"
                     34: #include "plist.h"
                     35: #include "log.h"
                     36: 
                     37: #include "ospfd/ospfd.h"
                     38: #include "ospfd/ospf_interface.h"
                     39: #include "ospfd/ospf_ism.h"
                     40: #include "ospfd/ospf_asbr.h"
                     41: #include "ospfd/ospf_lsa.h"
                     42: #include "ospfd/ospf_lsdb.h"
                     43: #include "ospfd/ospf_neighbor.h"
                     44: #include "ospfd/ospf_nsm.h"
                     45: #include "ospfd/ospf_spf.h"
                     46: #include "ospfd/ospf_route.h"
                     47: #include "ospfd/ospf_ia.h"
                     48: #include "ospfd/ospf_flood.h"
                     49: #include "ospfd/ospf_abr.h"
                     50: #include "ospfd/ospf_ase.h"
                     51: #include "ospfd/ospf_zebra.h"
                     52: #include "ospfd/ospf_dump.h"
                     53: 
                     54: static struct ospf_area_range *
                     55: ospf_area_range_new (struct prefix_ipv4 *p)
                     56: {
                     57:   struct ospf_area_range *range;
                     58: 
                     59:   range = XCALLOC (MTYPE_OSPF_AREA_RANGE, sizeof (struct ospf_area_range));
                     60:   range->addr = p->prefix;
                     61:   range->masklen = p->prefixlen;
                     62:   range->cost_config = OSPF_AREA_RANGE_COST_UNSPEC;
                     63: 
                     64:   return range;
                     65: }
                     66: 
                     67: static void
                     68: ospf_area_range_free (struct ospf_area_range *range)
                     69: {
                     70:   XFREE (MTYPE_OSPF_AREA_RANGE, range);
                     71: }
                     72: 
                     73: static void
                     74: ospf_area_range_add (struct ospf_area *area, struct ospf_area_range *range)
                     75: {
                     76:   struct route_node *rn;
                     77:   struct prefix_ipv4 p;
                     78: 
                     79:   p.family = AF_INET;
                     80:   p.prefixlen = range->masklen;
                     81:   p.prefix = range->addr;
                     82: 
                     83:   rn = route_node_get (area->ranges, (struct prefix *)&p);
                     84:   if (rn->info)
                     85:     route_unlock_node (rn);
                     86:   else
                     87:     rn->info = range;
                     88: }
                     89: 
                     90: static void
1.1.1.3 ! misho      91: ospf_area_range_delete (struct ospf_area *area, struct route_node *rn)
1.1       misho      92: {
1.1.1.3 ! misho      93:   struct ospf_area_range *range = rn->info;
1.1       misho      94: 
1.1.1.3 ! misho      95:   if (range->specifics != 0)
        !            96:     ospf_delete_discard_route (area->ospf->new_table,
        !            97:                               (struct prefix_ipv4 *) &rn->p);
        !            98: 
        !            99:   ospf_area_range_free (range);
        !           100:   rn->info = NULL;
        !           101:   route_unlock_node (rn);
        !           102:   route_unlock_node (rn);
1.1       misho     103: }
                    104: 
                    105: struct ospf_area_range *
                    106: ospf_area_range_lookup (struct ospf_area *area, struct prefix_ipv4 *p)
                    107: {
                    108:   struct route_node *rn;
                    109: 
                    110:   rn = route_node_lookup (area->ranges, (struct prefix *)p);
                    111:   if (rn)
                    112:     {
                    113:       route_unlock_node (rn);
                    114:       return rn->info;
                    115:     }
                    116:   return NULL;
                    117: }
                    118: 
                    119: struct ospf_area_range *
                    120: ospf_area_range_lookup_next (struct ospf_area *area, 
                    121:                              struct in_addr *range_net,
                    122:                              int first)
                    123: {
                    124:   struct route_node *rn;
                    125:   struct prefix_ipv4 p;
                    126:   struct ospf_area_range *find;
                    127: 
                    128:   p.family = AF_INET;
                    129:   p.prefixlen = IPV4_MAX_BITLEN;
                    130:   p.prefix = *range_net;
                    131: 
                    132:   if (first)
                    133:     rn = route_top (area->ranges);
                    134:   else
                    135:     {
                    136:       rn = route_node_get (area->ranges, (struct prefix *) &p);
                    137:       rn = route_next (rn);
                    138:     }
                    139: 
                    140:   for (; rn; rn = route_next (rn))
                    141:     if (rn->info)
                    142:       break;
                    143: 
                    144:   if (rn && rn->info)
                    145:     {
                    146:       find = rn->info;
                    147:       *range_net = rn->p.u.prefix4;
                    148:       route_unlock_node (rn);
                    149:       return find;
                    150:     }
                    151:   return NULL;
                    152: }
                    153: 
                    154: static struct ospf_area_range *
                    155: ospf_area_range_match (struct ospf_area *area, struct prefix_ipv4 *p)
                    156: {
                    157:   struct route_node *node;
                    158: 
                    159:   node = route_node_match (area->ranges, (struct prefix *) p);
                    160:   if (node)
                    161:     {
                    162:       route_unlock_node (node);
                    163:       return node->info;
                    164:     }
                    165:   return NULL;
                    166: }
                    167: 
                    168: struct ospf_area_range *
                    169: ospf_area_range_match_any (struct ospf *ospf, struct prefix_ipv4 *p)
                    170: {
                    171:   struct ospf_area_range *range;
                    172:   struct ospf_area *area;
                    173:   struct listnode *node;
                    174: 
                    175:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                    176:     if ((range = ospf_area_range_match (area, p)))
                    177:       return range;
                    178: 
                    179:   return NULL;
                    180: }
                    181: 
                    182: int
                    183: ospf_area_range_active (struct ospf_area_range *range)
                    184: {
                    185:   return range->specifics;
                    186: }
                    187: 
                    188: static int
                    189: ospf_area_actively_attached (struct ospf_area *area)
                    190: {
                    191:   return area->act_ints;
                    192: }
                    193: 
                    194: int
                    195: ospf_area_range_set (struct ospf *ospf, struct in_addr area_id,
                    196:                     struct prefix_ipv4 *p, int advertise)
                    197: {
                    198:   struct ospf_area *area;
                    199:   struct ospf_area_range *range;
                    200:   int ret = OSPF_AREA_ID_FORMAT_ADDRESS;
                    201: 
                    202:   area = ospf_area_get (ospf, area_id, ret);
                    203:   if (area == NULL)
                    204:     return 0;
                    205: 
                    206:   range = ospf_area_range_lookup (area, p);
                    207:   if (range != NULL)
                    208:     {
                    209:       if ((CHECK_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE)
                    210:           && !CHECK_FLAG (advertise, OSPF_AREA_RANGE_ADVERTISE))
                    211:          || (!CHECK_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE)
                    212:              && CHECK_FLAG (advertise, OSPF_AREA_RANGE_ADVERTISE)))
                    213:        ospf_schedule_abr_task (ospf);
                    214:     }
                    215:   else
                    216:     {
                    217:       range = ospf_area_range_new (p);
                    218:       ospf_area_range_add (area, range);
                    219:       ospf_schedule_abr_task (ospf);
                    220:     }
                    221: 
                    222:   if (CHECK_FLAG (advertise, OSPF_AREA_RANGE_ADVERTISE))
                    223:     SET_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE);
                    224:   else
                    225:     UNSET_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE);
                    226: 
                    227:   return 1;
                    228: }
                    229: 
                    230: int
                    231: ospf_area_range_cost_set (struct ospf *ospf, struct in_addr area_id,
                    232:                          struct prefix_ipv4 *p, u_int32_t cost)
                    233: {
                    234:   struct ospf_area *area;
                    235:   struct ospf_area_range *range;
                    236:   int ret = OSPF_AREA_ID_FORMAT_ADDRESS;
                    237: 
                    238:   area = ospf_area_get (ospf, area_id, ret);
                    239:   if (area == NULL)
                    240:     return 0;
                    241: 
                    242:   range = ospf_area_range_lookup (area, p);
                    243:   if (range == NULL)
                    244:     return 0;
                    245: 
                    246:   if (range->cost_config != cost)
                    247:     {
                    248:       range->cost_config = cost;
                    249:       if (ospf_area_range_active (range))
                    250:        ospf_schedule_abr_task (ospf);
                    251:     }
                    252: 
                    253:   return 1;
                    254: }
                    255: 
                    256: int
                    257: ospf_area_range_unset (struct ospf *ospf, struct in_addr area_id,
                    258:                       struct prefix_ipv4 *p)
                    259: {
                    260:   struct ospf_area *area;
1.1.1.3 ! misho     261:   struct route_node *rn;
1.1       misho     262: 
                    263:   area = ospf_area_lookup_by_area_id (ospf, area_id);
                    264:   if (area == NULL)
                    265:     return 0;
                    266: 
1.1.1.3 ! misho     267:   rn = route_node_lookup (area->ranges, (struct prefix*)p);
        !           268:   if (rn == NULL)
1.1       misho     269:     return 0;
                    270: 
1.1.1.3 ! misho     271:   if (ospf_area_range_active (rn->info))
1.1       misho     272:     ospf_schedule_abr_task (ospf);
                    273: 
1.1.1.3 ! misho     274:   ospf_area_range_delete (area, rn);
1.1       misho     275: 
                    276:   return 1;
                    277: }
                    278: 
                    279: int
                    280: ospf_area_range_substitute_set (struct ospf *ospf, struct in_addr area_id,
                    281:                                struct prefix_ipv4 *p, struct prefix_ipv4 *s)
                    282: {
                    283:   struct ospf_area *area;
                    284:   struct ospf_area_range *range;
                    285:   int ret = OSPF_AREA_ID_FORMAT_ADDRESS;
                    286: 
                    287:   area = ospf_area_get (ospf, area_id, ret);
                    288:   range = ospf_area_range_lookup (area, p);
                    289: 
                    290:   if (range != NULL)
                    291:     {
                    292:       if (!CHECK_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE) ||
                    293:          !CHECK_FLAG (range->flags, OSPF_AREA_RANGE_SUBSTITUTE))
                    294:        ospf_schedule_abr_task (ospf);
                    295:     }
                    296:   else
                    297:     {
                    298:       range = ospf_area_range_new (p);
                    299:       ospf_area_range_add (area, range);
                    300:       ospf_schedule_abr_task (ospf);
                    301:     }
                    302: 
                    303:   SET_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE);
                    304:   SET_FLAG (range->flags, OSPF_AREA_RANGE_SUBSTITUTE);
                    305:   range->subst_addr = s->prefix;
                    306:   range->subst_masklen = s->prefixlen;
                    307: 
                    308:   return 1;
                    309: }
                    310: 
                    311: int
                    312: ospf_area_range_substitute_unset (struct ospf *ospf, struct in_addr area_id,
                    313:                                  struct prefix_ipv4 *p)
                    314: {
                    315:   struct ospf_area *area;
                    316:   struct ospf_area_range *range;
                    317: 
                    318:   area = ospf_area_lookup_by_area_id (ospf, area_id);
                    319:   if (area == NULL)
                    320:     return 0;
                    321: 
                    322:   range = ospf_area_range_lookup (area, p);
                    323:   if (range == NULL)
                    324:     return 0;
                    325: 
                    326:   if (CHECK_FLAG (range->flags, OSPF_AREA_RANGE_SUBSTITUTE))
                    327:     if (ospf_area_range_active (range))
                    328:       ospf_schedule_abr_task (ospf);
                    329: 
                    330:   UNSET_FLAG (range->flags, OSPF_AREA_RANGE_SUBSTITUTE);
                    331:   range->subst_addr.s_addr = 0;
                    332:   range->subst_masklen = 0;
                    333: 
                    334:   return 1;
                    335: }
                    336: 
                    337: int
                    338: ospf_act_bb_connection (struct ospf *ospf)
                    339: {
                    340:   if (ospf->backbone == NULL)
                    341:     return 0;
                    342: 
                    343:   return ospf->backbone->full_nbrs;
                    344: }
                    345: 
                    346: /* Determine whether this router is elected translator or not for area */
                    347: static int
                    348: ospf_abr_nssa_am_elected (struct ospf_area *area)
                    349: {
                    350:   struct route_node *rn;
                    351:   struct ospf_lsa *lsa;
                    352:   struct router_lsa *rlsa;
                    353:   struct in_addr *best = NULL;
                    354:   
                    355:   LSDB_LOOP ( ROUTER_LSDB (area), rn, lsa)
                    356:     {
                    357:       /* sanity checks */
                    358:       if (!lsa 
                    359:           || (lsa->data->type != OSPF_ROUTER_LSA) 
                    360:           || IS_LSA_SELF (lsa))
                    361:         continue;
                    362:       
                    363:       rlsa = (struct router_lsa *) lsa->data;
                    364:       
                    365:       /* ignore non-ABR routers */
                    366:       if (!IS_ROUTER_LSA_BORDER (rlsa))
                    367:         continue;
                    368:       
                    369:       /* Router has Nt flag - always translate */
                    370:       if (IS_ROUTER_LSA_NT (rlsa))
                    371:         {
                    372:           if (IS_DEBUG_OSPF_NSSA)
                    373:             zlog_debug ("ospf_abr_nssa_am_elected: "
                    374:                        "router %s asserts Nt",
                    375:                        inet_ntoa (lsa->data->id) );
                    376:           return 0;
                    377:         }
                    378:       
                    379:       if (best == NULL)
                    380:        best = &lsa->data->id;
                    381:       else
1.1.1.2   misho     382:         if (IPV4_ADDR_CMP (&best->s_addr, &lsa->data->id.s_addr) < 0)
1.1       misho     383:           best = &lsa->data->id;
                    384:     }
                    385:     
                    386:     if (IS_DEBUG_OSPF_NSSA)
                    387:       zlog_debug ("ospf_abr_nssa_am_elected: best electable ABR is: %s",
                    388:                   (best) ? inet_ntoa (*best) : "<none>" );
                    389:                   
                    390:     if (best == NULL)
                    391:       return 1;
                    392:     
1.1.1.2   misho     393:     if (IPV4_ADDR_CMP (&best->s_addr, &area->ospf->router_id.s_addr) < 0)
1.1       misho     394:       return 1;
                    395:     else
                    396:       return 0;
                    397: }
                    398: 
                    399: /* Check NSSA ABR status
                    400:  * assumes there are nssa areas
                    401:  */
                    402: static void 
                    403: ospf_abr_nssa_check_status (struct ospf *ospf)
                    404: {
                    405:   struct ospf_area *area;
                    406:   struct listnode *lnode, *nnode;
                    407:   
                    408:   for (ALL_LIST_ELEMENTS (ospf->areas, lnode, nnode, area))
                    409:     {
                    410:       u_char old_state = area->NSSATranslatorState;
                    411: 
                    412:       if (area->external_routing != OSPF_AREA_NSSA)
                    413:         continue;
                    414: 
                    415:       if (IS_DEBUG_OSPF (nssa, NSSA))
                    416:         zlog_debug ("ospf_abr_nssa_check_status: "
                    417:                     "checking area %s",
                    418:                     inet_ntoa (area->area_id));
                    419: 
                    420:       if (!IS_OSPF_ABR (area->ospf))
                    421:         {
                    422:           if (IS_DEBUG_OSPF (nssa, NSSA))
                    423:             zlog_debug ("ospf_abr_nssa_check_status: " 
                    424:                         "not ABR");
                    425:           area->NSSATranslatorState = OSPF_NSSA_TRANSLATE_DISABLED;
                    426:         }
                    427:       else
                    428:         {
                    429:           switch (area->NSSATranslatorRole)
                    430:             {
                    431:             case OSPF_NSSA_ROLE_NEVER:
                    432:               /* We never Translate Type-7 LSA. */
                    433:               /* TODO: check previous state and flush? */
                    434:               if (IS_DEBUG_OSPF (nssa, NSSA))
                    435:                 zlog_debug ("ospf_abr_nssa_check_status: "
                    436:                            "never translate");
                    437:               area->NSSATranslatorState = OSPF_NSSA_TRANSLATE_DISABLED;
                    438:               break;
                    439: 
                    440:             case OSPF_NSSA_ROLE_ALWAYS:
                    441:               /* We always translate if we are an ABR
                    442:                * TODO: originate new LSAs if state change?
                    443:                * or let the nssa abr task take care of it?
                    444:                */
                    445:               if (IS_DEBUG_OSPF (nssa, NSSA))
                    446:                 zlog_debug ("ospf_abr_nssa_check_status: "
                    447:                             "translate always");
                    448:               area->NSSATranslatorState = OSPF_NSSA_TRANSLATE_ENABLED;
                    449:               break;
                    450: 
                    451:             case OSPF_NSSA_ROLE_CANDIDATE:
                    452:               /* We are a candidate for Translation */
                    453:               if (ospf_abr_nssa_am_elected (area) > 0)
                    454:                 {
                    455:                   area->NSSATranslatorState = OSPF_NSSA_TRANSLATE_ENABLED;
                    456:                   if (IS_DEBUG_OSPF (nssa, NSSA))
                    457:                     zlog_debug ("ospf_abr_nssa_check_status: "
                    458:                                 "elected translator");
                    459:                 }
                    460:               else
                    461:                 {
                    462:                   area->NSSATranslatorState = OSPF_NSSA_TRANSLATE_DISABLED;
                    463:                   if (IS_DEBUG_OSPF (nssa, NSSA))
                    464:                     zlog_debug ("ospf_abr_nssa_check_status: " "not elected");
                    465:                 }
                    466:               break;
                    467:             }
                    468:         }
                    469:       /* RFC3101, 3.1:
                    470:        * All NSSA border routers must set the E-bit in the Type-1 router-LSAs
                    471:        * of their directly attached non-stub areas, even when they are not
                    472:        * translating.
                    473:        */
                    474:       if (old_state != area->NSSATranslatorState)
                    475:        {
                    476:           if (old_state == OSPF_NSSA_TRANSLATE_DISABLED)
                    477:            ospf_asbr_status_update (ospf, ++ospf->redistribute);
                    478:          else if (area->NSSATranslatorState == OSPF_NSSA_TRANSLATE_DISABLED)
                    479:            ospf_asbr_status_update (ospf, --ospf->redistribute);
                    480:        }
                    481:     }
                    482: }
                    483: 
                    484: /* Check area border router status. */
                    485: void
                    486: ospf_check_abr_status (struct ospf *ospf)
                    487: {
                    488:   struct ospf_area *area;
                    489:   struct listnode *node, *nnode;
                    490:   int bb_configured = 0;
                    491:   int bb_act_attached = 0;
                    492:   int areas_configured = 0;
                    493:   int areas_act_attached = 0;
                    494:   u_char new_flags = ospf->flags;
                    495: 
                    496:   if (IS_DEBUG_OSPF_EVENT)
                    497:     zlog_debug ("ospf_check_abr_status(): Start");
                    498: 
                    499:   for (ALL_LIST_ELEMENTS (ospf->areas, node, nnode, area))
                    500:     {
                    501:       if (listcount (area->oiflist)) 
                    502:        {
                    503:          areas_configured++;
                    504:          
                    505:          if (OSPF_IS_AREA_BACKBONE (area))
                    506:            bb_configured = 1;
                    507:        }
                    508: 
                    509:       if (ospf_area_actively_attached (area))
                    510:        {
                    511:          areas_act_attached++;
                    512:          
                    513:          if (OSPF_IS_AREA_BACKBONE (area))
                    514:             bb_act_attached = 1;
                    515:        }
                    516:     }
                    517: 
                    518:   if (IS_DEBUG_OSPF_EVENT)
                    519:     {
                    520:       zlog_debug ("ospf_check_abr_status(): looked through areas");
                    521:       zlog_debug ("ospf_check_abr_status(): bb_configured: %d", bb_configured);
                    522:       zlog_debug ("ospf_check_abr_status(): bb_act_attached: %d",
                    523:                 bb_act_attached);
                    524:       zlog_debug ("ospf_check_abr_status(): areas_configured: %d",
                    525:                 areas_configured);
                    526:       zlog_debug ("ospf_check_abr_status(): areas_act_attached: %d",
                    527:                 areas_act_attached);
                    528:     }
                    529: 
                    530:   switch (ospf->abr_type)
                    531:     {
                    532:     case OSPF_ABR_SHORTCUT:
                    533:     case OSPF_ABR_STAND:
                    534:       if (areas_act_attached > 1)
                    535:        SET_FLAG (new_flags, OSPF_FLAG_ABR);
                    536:       else
                    537:        UNSET_FLAG (new_flags, OSPF_FLAG_ABR);
                    538:       break;
                    539: 
                    540:     case OSPF_ABR_IBM:
                    541:       if ((areas_act_attached > 1) && bb_configured)
                    542:        SET_FLAG (new_flags, OSPF_FLAG_ABR);
                    543:       else
                    544:        UNSET_FLAG (new_flags, OSPF_FLAG_ABR);
                    545:       break;
                    546: 
                    547:     case OSPF_ABR_CISCO:
                    548:       if ((areas_configured > 1) && bb_act_attached)
                    549:        SET_FLAG (new_flags, OSPF_FLAG_ABR);
                    550:       else
                    551:        UNSET_FLAG (new_flags, OSPF_FLAG_ABR);
                    552:       break;
                    553:     default:
                    554:       break;
                    555:     }
                    556: 
                    557:   if (new_flags != ospf->flags)
                    558:     {
                    559:       ospf_spf_calculate_schedule (ospf);
                    560:       if (IS_DEBUG_OSPF_EVENT)
                    561:        zlog_debug ("ospf_check_abr_status(): new router flags: %x",new_flags);
                    562:       ospf->flags = new_flags;
                    563:       ospf_router_lsa_update (ospf);
                    564:     }
                    565: }
                    566: 
                    567: static void
                    568: ospf_abr_update_aggregate (struct ospf_area_range *range,
1.1.1.3 ! misho     569:                            struct ospf_route *or, struct ospf_area *area)
1.1       misho     570: {
                    571:   if (IS_DEBUG_OSPF_EVENT)
                    572:     zlog_debug ("ospf_abr_update_aggregate(): Start");
                    573: 
1.1.1.3 ! misho     574:   if (CHECK_FLAG (area->stub_router_state, OSPF_AREA_IS_STUB_ROUTED) &&
        !           575:       (range->cost != OSPF_STUB_MAX_METRIC_SUMMARY_COST))
        !           576:     {
        !           577:       range->cost = OSPF_STUB_MAX_METRIC_SUMMARY_COST;
        !           578:       if (IS_DEBUG_OSPF_EVENT)
        !           579:         zlog_debug ("ospf_abr_update_aggregate(): use summary max-metric 0x%08x",
        !           580:                    range->cost);
        !           581:     }
        !           582:   else if (range->cost_config != OSPF_AREA_RANGE_COST_UNSPEC)
1.1       misho     583:     {
                    584:       if (IS_DEBUG_OSPF_EVENT)
                    585:         zlog_debug ("ospf_abr_update_aggregate(): use configured cost %d",
                    586:                    range->cost_config);
                    587: 
                    588:       range->cost = range->cost_config;
                    589:     }
                    590:   else
                    591:     {
                    592:       if (range->specifics == 0)
1.1.1.3 ! misho     593:        {
        !           594:          if (IS_DEBUG_OSPF_EVENT)
        !           595:            zlog_debug ("ospf_abr_update_aggregate(): use or->cost %d",
        !           596:                        or->cost);
        !           597: 
        !           598:          range->cost = or->cost; /* 1st time get 1st cost */
        !           599:        }
1.1       misho     600: 
                    601:       if (or->cost > range->cost)
                    602:         {
                    603:           if (IS_DEBUG_OSPF_EVENT)
1.1.1.3 ! misho     604:             zlog_debug ("ospf_abr_update_aggregate(): update to %d", or->cost);
1.1       misho     605: 
                    606:           range->cost = or->cost;
                    607:         }
                    608:     }
                    609: 
                    610:   range->specifics++;
                    611: }
                    612: 
                    613: static void
                    614: set_metric (struct ospf_lsa *lsa, u_int32_t metric)
                    615: {
                    616:   struct summary_lsa *header;
                    617:   u_char *mp;
                    618:   metric = htonl (metric);
                    619:   mp = (u_char *) &metric;
                    620:   mp++;
                    621:   header = (struct summary_lsa *) lsa->data;
                    622:   memcpy(header->metric, mp, 3);
                    623: }
                    624: 
                    625: /* ospf_abr_translate_nssa */
                    626: static int
                    627: ospf_abr_translate_nssa (struct ospf_area *area, struct ospf_lsa *lsa)
                    628: {
                    629:   /* Incoming Type-7 or later aggregated Type-7 
                    630:    *
                    631:    * LSA is skipped if P-bit is off.
                    632:    * LSA is aggregated if within range.
                    633:    *
                    634:    * The Type-7 is translated, Installed/Approved as a Type-5 into
                    635:    * global LSDB, then Flooded through AS
                    636:    *
                    637:    *  Later, any Unapproved Translated Type-5's are flushed/discarded 
                    638:    */
                    639: 
                    640:   struct ospf_lsa *old = NULL,
                    641:                   *new = NULL;
                    642:   struct as_external_lsa *ext7;
                    643:   struct prefix_ipv4 p;
                    644: 
                    645:   if (! CHECK_FLAG (lsa->data->options, OSPF_OPTION_NP))
                    646:     {
                    647:       if (IS_DEBUG_OSPF_NSSA)
                    648:         zlog_debug ("ospf_abr_translate_nssa(): LSA Id %s, P-bit off, NO Translation",
                    649:                    inet_ntoa (lsa->data->id));
                    650:       return 1; 
                    651:     }
                    652:   
                    653:   if (IS_DEBUG_OSPF_NSSA)
                    654:     zlog_debug ("ospf_abr_translate_nssa(): LSA Id %s, TRANSLATING 7 to 5",
                    655:                inet_ntoa (lsa->data->id));
                    656: 
                    657:   ext7 = (struct as_external_lsa *)(lsa->data);
                    658:   p.prefix = lsa->data->id;
                    659:   p.prefixlen = ip_masklen (ext7->mask);
                    660:   
                    661:   if (ext7->e[0].fwd_addr.s_addr == OSPF_DEFAULT_DESTINATION)
                    662:     {
                    663:       if (IS_DEBUG_OSPF_NSSA)
                    664:         zlog_debug ("ospf_abr_translate_nssa(): LSA Id %s, "
                    665:                    "Forward address is 0, NO Translation",
                    666:                    inet_ntoa (lsa->data->id));
                    667:       return 1;
                    668:     }
                    669:   
                    670:   /* try find existing AS-External LSA for this prefix */
                    671: 
                    672:   old = ospf_external_info_find_lsa (area->ospf, &p);
                    673: 
                    674:   if (old)
                    675:     {
                    676:       if (IS_DEBUG_OSPF_NSSA)
                    677:         zlog_debug ("ospf_abr_translate_nssa(): " 
                    678:                    "found old translated LSA Id %s, refreshing",
                    679:                    inet_ntoa (old->data->id));
                    680:             
                    681:       /* refresh */
                    682:       new = ospf_translated_nssa_refresh (area->ospf, lsa, old);
                    683:       if (!new)
                    684:         {
                    685:           if (IS_DEBUG_OSPF_NSSA)
                    686:             zlog_debug ("ospf_abr_translate_nssa(): "
                    687:               "could not refresh translated LSA Id %s",
                    688:               inet_ntoa (old->data->id));
                    689:         }
                    690:     }
                    691:   else
                    692:     {
                    693:       /* no existing external route for this LSA Id
                    694:        * originate translated LSA 
                    695:        */
                    696:       
                    697:          if ((new = ospf_translated_nssa_originate (area->ospf, lsa)) 
                    698:               == NULL)
                    699:            {
                    700:              if (IS_DEBUG_OSPF_NSSA)
                    701:                zlog_debug ("ospf_abr_translate_nssa(): Could not translate "
                    702:                           "Type-7 for %s to Type-5", 
                    703:                           inet_ntoa (lsa->data->id));
                    704:                return 1;
                    705:            }
                    706:     }
                    707: 
                    708:   /* Area where Aggregate testing will be inserted, just like summary
                    709:      advertisements */
                    710:   /* ospf_abr_check_nssa_range (p_arg, lsa-> cost, lsa -> area); */
                    711: 
                    712:   return 0;
                    713: }
                    714: 
                    715: static void
                    716: ospf_abr_translate_nssa_range (struct prefix_ipv4 *p, u_int32_t cost)
                    717: {
                    718:   /* The Type-7 is created from the aggregated prefix and forwarded
                    719:      for lsa installation and flooding... to be added... */
                    720: }
                    721: 
                    722: void
                    723: ospf_abr_announce_network_to_area (struct prefix_ipv4 *p, u_int32_t cost,
                    724:                                   struct ospf_area *area)
                    725: {
                    726:   struct ospf_lsa *lsa, *old = NULL;
                    727:   struct summary_lsa *sl = NULL;
1.1.1.3 ! misho     728:   u_int32_t full_cost;
1.1       misho     729: 
                    730:   if (IS_DEBUG_OSPF_EVENT)
                    731:     zlog_debug ("ospf_abr_announce_network_to_area(): Start");
                    732: 
1.1.1.3 ! misho     733:   if (CHECK_FLAG (area->stub_router_state, OSPF_AREA_IS_STUB_ROUTED))
        !           734:     full_cost = OSPF_STUB_MAX_METRIC_SUMMARY_COST;
        !           735:   else
        !           736:     full_cost = cost;
        !           737: 
1.1       misho     738:   old = ospf_lsa_lookup_by_prefix (area->lsdb, OSPF_SUMMARY_LSA, 
                    739:                                    (struct prefix_ipv4 *) p,
                    740:                                    area->ospf->router_id);
                    741:   if (old)
                    742:     {
                    743:       if (IS_DEBUG_OSPF_EVENT)
                    744:         zlog_debug ("ospf_abr_announce_network_to_area(): old summary found");
                    745: 
                    746:       sl = (struct summary_lsa *) old->data;
                    747: 
                    748:       if (IS_DEBUG_OSPF_EVENT)
                    749:         zlog_debug ("ospf_abr_announce_network_to_area(): "
                    750:                   "old metric: %d, new metric: %d",
                    751:                GET_METRIC (sl->metric), cost);
1.1.1.3 ! misho     752: 
        !           753:       if ((GET_METRIC (sl->metric) == full_cost) &&
        !           754:          ((old->flags & OSPF_LSA_IN_MAXAGE) == 0))
1.1       misho     755:         {
                    756:           /* unchanged. simply reapprove it */
                    757:           if (IS_DEBUG_OSPF_EVENT)
                    758:             zlog_debug ("ospf_abr_announce_network_to_area(): "
                    759:                        "old summary approved"); 
                    760:           SET_FLAG (old->flags, OSPF_LSA_APPROVED);
                    761:         }
                    762:       else
                    763:         {
                    764:           /* LSA is changed, refresh it */
                    765:           if (IS_DEBUG_OSPF_EVENT)
                    766:             zlog_debug ("ospf_abr_announce_network_to_area(): "
                    767:                        "refreshing summary");
1.1.1.3 ! misho     768:           set_metric (old, full_cost);
1.1       misho     769:           lsa = ospf_lsa_refresh (area->ospf, old);
                    770:           
                    771:           if (!lsa)
                    772:             {
                    773:              char buf[INET_ADDRSTRLEN + 3]; /* ipv4 and /XX */
                    774:              
                    775:              prefix2str ((struct prefix *) p, buf, sizeof(buf));
                    776:              zlog_warn ("%s: Could not refresh %s to %s",
                    777:                         __func__,
                    778:                         buf,
                    779:                         inet_ntoa (area->area_id));
                    780:              return;
                    781:            }
                    782:          
                    783:           SET_FLAG (lsa->flags, OSPF_LSA_APPROVED);
                    784:           /* This will flood through area. */
                    785:         }
                    786:     }
                    787:   else
                    788:     {
                    789:       if (IS_DEBUG_OSPF_EVENT)
                    790:         zlog_debug ("ospf_abr_announce_network_to_area(): "
                    791:                   "creating new summary");
1.1.1.3 ! misho     792:       lsa = ospf_summary_lsa_originate ( (struct prefix_ipv4 *)p, full_cost, area);
1.1       misho     793:           /* This will flood through area. */
                    794:       
                    795:       if (!lsa)
                    796:        {
                    797:          char buf[INET_ADDRSTRLEN + 3]; /* ipv4 and /XX */
                    798:          
                    799:          prefix2str ((struct prefix *)p, buf, sizeof(buf));
                    800:          zlog_warn ("%s: Could not originate %s to %s",
                    801:                     __func__,
                    802:                     buf,
                    803:                     inet_ntoa (area->area_id));
                    804:          return;
                    805:        }
                    806:       
                    807:       SET_FLAG (lsa->flags, OSPF_LSA_APPROVED);
                    808:       if (IS_DEBUG_OSPF_EVENT)
                    809:         zlog_debug ("ospf_abr_announce_network_to_area(): "
                    810:                   "flooding new version of summary");
                    811:     }
                    812: 
                    813:   if (IS_DEBUG_OSPF_EVENT)
                    814:     zlog_debug ("ospf_abr_announce_network_to_area(): Stop");
                    815: }
                    816: 
                    817: static int
                    818: ospf_abr_nexthops_belong_to_area (struct ospf_route *or,
                    819:                                  struct ospf_area *area)
                    820: {
                    821:   struct listnode *node, *nnode;
                    822:   struct ospf_path *path;
                    823:   struct ospf_interface *oi;
                    824: 
                    825:   for (ALL_LIST_ELEMENTS_RO (or->paths, node, path))
                    826:     for (ALL_LIST_ELEMENTS_RO (area->oiflist, nnode, oi))
                    827:       if (oi->ifp && oi->ifp->ifindex == path->ifindex)
                    828:        return 1;
                    829: 
                    830:   return 0;
                    831: }
                    832: 
                    833: static int
                    834: ospf_abr_should_accept (struct prefix_ipv4 *p, struct ospf_area *area)
                    835: {
                    836:   if (IMPORT_NAME (area))
                    837:     {
                    838:       if (IMPORT_LIST (area) == NULL)
                    839:        IMPORT_LIST (area) = access_list_lookup (AFI_IP, IMPORT_NAME (area));
                    840: 
                    841:       if (IMPORT_LIST (area))
                    842:         if (access_list_apply (IMPORT_LIST (area), p) == FILTER_DENY)
                    843:            return 0;
                    844:     }
                    845: 
                    846:  return 1;
                    847: }
                    848: 
                    849: static int
                    850: ospf_abr_plist_in_check (struct ospf_area *area, struct ospf_route *or,
                    851:                         struct prefix_ipv4 *p)
                    852: {
                    853:   if (PREFIX_NAME_IN (area))
                    854:     {
                    855:       if (PREFIX_LIST_IN (area) == NULL)
                    856:        PREFIX_LIST_IN (area) = prefix_list_lookup (AFI_IP,
                    857:                                                    PREFIX_NAME_IN (area));
                    858:       if (PREFIX_LIST_IN (area))
                    859:        if (prefix_list_apply (PREFIX_LIST_IN (area), p) != PREFIX_PERMIT)
                    860:          return 0;
                    861:     }
                    862:   return 1;
                    863: }
                    864: 
                    865: static int
                    866: ospf_abr_plist_out_check (struct ospf_area *area, struct ospf_route *or,
                    867:                          struct prefix_ipv4 *p)
                    868: {
                    869:   if (PREFIX_NAME_OUT (area))
                    870:     {
                    871:       if (PREFIX_LIST_OUT (area) == NULL)
                    872:        PREFIX_LIST_OUT (area) = prefix_list_lookup (AFI_IP,
                    873:                                                     PREFIX_NAME_OUT (area));
                    874:       if (PREFIX_LIST_OUT (area))
                    875:        if (prefix_list_apply (PREFIX_LIST_OUT (area), p) != PREFIX_PERMIT)
                    876:          return 0;
                    877:     }
                    878:   return 1;
                    879: }
                    880: 
                    881: static void
                    882: ospf_abr_announce_network (struct ospf *ospf,
                    883:                           struct prefix_ipv4 *p, struct ospf_route *or)
                    884: {
                    885:   struct ospf_area_range *range;
                    886:   struct ospf_area *area, *or_area;
                    887:   struct listnode *node;
                    888: 
                    889:   if (IS_DEBUG_OSPF_EVENT)
                    890:     zlog_debug ("ospf_abr_announce_network(): Start");
                    891: 
                    892:   or_area = ospf_area_lookup_by_area_id (ospf, or->u.std.area_id); 
                    893:   assert (or_area);
                    894: 
                    895:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                    896:     {
                    897:       if (IS_DEBUG_OSPF_EVENT)
                    898:        zlog_debug ("ospf_abr_announce_network(): looking at area %s",
                    899:                   inet_ntoa (area->area_id));
                    900: 
                    901:       if (IPV4_ADDR_SAME (&or->u.std.area_id, &area->area_id))
                    902:        continue;
                    903: 
                    904:       if (ospf_abr_nexthops_belong_to_area (or, area))
                    905:        continue;
                    906: 
                    907:       if (!ospf_abr_should_accept (p, area))
                    908:        {
                    909:          if (IS_DEBUG_OSPF_EVENT)
                    910:            zlog_debug ("ospf_abr_announce_network(): "
                    911:                       "prefix %s/%d was denied by import-list",
                    912:                       inet_ntoa (p->prefix), p->prefixlen);
                    913:          continue; 
                    914:        }
                    915: 
                    916:       if (!ospf_abr_plist_in_check (area, or, p))
                    917:        {
                    918:          if (IS_DEBUG_OSPF_EVENT)
                    919:            zlog_debug ("ospf_abr_announce_network(): "
                    920:                       "prefix %s/%d was denied by prefix-list",
                    921:                       inet_ntoa (p->prefix), p->prefixlen);
                    922:          continue; 
                    923:        }
                    924: 
                    925:       if (area->external_routing != OSPF_AREA_DEFAULT && area->no_summary)
                    926:        {
                    927:          if (IS_DEBUG_OSPF_EVENT)
                    928:            zlog_debug ("ospf_abr_announce_network(): "
                    929:                       "area %s is stub and no_summary",
                    930:                       inet_ntoa (area->area_id));
                    931:           continue;
                    932:        }
                    933: 
                    934:       if (or->path_type == OSPF_PATH_INTER_AREA)
                    935:        {
                    936:          if (IS_DEBUG_OSPF_EVENT)
                    937:            zlog_debug ("ospf_abr_announce_network(): this is "
                    938:                       "inter-area route to %s/%d",
                    939:                       inet_ntoa (p->prefix), p->prefixlen);
                    940: 
                    941:           if (!OSPF_IS_AREA_BACKBONE (area))
                    942:            ospf_abr_announce_network_to_area (p, or->cost, area);
                    943:        }
                    944: 
                    945:       if (or->path_type == OSPF_PATH_INTRA_AREA)
                    946:         {
                    947:           if (IS_DEBUG_OSPF_EVENT)
                    948:             zlog_debug ("ospf_abr_announce_network(): "
                    949:                        "this is intra-area route to %s/%d",
                    950:                        inet_ntoa (p->prefix), p->prefixlen);
                    951:             if ((range = ospf_area_range_match (or_area, p)) 
                    952:                  && !ospf_area_is_transit (area))
1.1.1.3 ! misho     953:               ospf_abr_update_aggregate (range, or, area);
1.1       misho     954:             else
                    955:               ospf_abr_announce_network_to_area (p, or->cost, area);
                    956:         }
                    957:     }
                    958: }
                    959: 
                    960: static int
                    961: ospf_abr_should_announce (struct ospf *ospf,
                    962:                          struct prefix_ipv4 *p, struct ospf_route *or)
                    963: {
                    964:   struct ospf_area *area;
                    965: 
                    966:   area = ospf_area_lookup_by_area_id (ospf, or->u.std.area_id);
                    967: 
                    968:   assert (area);
                    969:   
                    970:   if (EXPORT_NAME (area))
                    971:     {
                    972:       if (EXPORT_LIST (area) == NULL)
                    973:        EXPORT_LIST (area) = access_list_lookup (AFI_IP, EXPORT_NAME (area));
                    974: 
                    975:       if (EXPORT_LIST (area))
                    976:         if (access_list_apply (EXPORT_LIST (area), p) == FILTER_DENY)
                    977:            return 0;
                    978:     }
                    979: 
                    980:   return 1;
                    981: }
                    982: 
                    983: static void
                    984: ospf_abr_process_nssa_translates (struct ospf *ospf)
                    985: {
                    986:   /* Scan through all NSSA_LSDB records for all areas;
                    987: 
                    988:      If P-bit is on, translate all Type-7's to 5's and aggregate or
                    989:      flood install as approved in Type-5 LSDB with XLATE Flag on
                    990:      later, do same for all aggregates...  At end, DISCARD all
                    991:      remaining UNAPPROVED Type-5's (Aggregate is for future ) */
                    992:   struct listnode *node;
                    993:   struct ospf_area *area;
                    994:   struct route_node *rn;
                    995:   struct ospf_lsa *lsa;
                    996: 
                    997:   if (IS_DEBUG_OSPF_NSSA)
                    998:     zlog_debug ("ospf_abr_process_nssa_translates(): Start");
                    999: 
                   1000:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1001:     {
                   1002:       if (! area->NSSATranslatorState)
                   1003:         continue; /* skip if not translator */
                   1004:       
                   1005:       if (area->external_routing != OSPF_AREA_NSSA)
                   1006:         continue;  /* skip if not Nssa Area */
                   1007: 
                   1008:       if (IS_DEBUG_OSPF_NSSA)
                   1009:         zlog_debug ("ospf_abr_process_nssa_translates(): "
                   1010:                    "looking at area %s", inet_ntoa (area->area_id));
                   1011:       
                   1012:       LSDB_LOOP (NSSA_LSDB (area), rn, lsa)
                   1013:         ospf_abr_translate_nssa (area, lsa);
                   1014:     }
                   1015:  
                   1016:   if (IS_DEBUG_OSPF_NSSA)
                   1017:     zlog_debug ("ospf_abr_process_nssa_translates(): Stop");
                   1018: 
                   1019: }
                   1020: 
                   1021: static void
                   1022: ospf_abr_process_network_rt (struct ospf *ospf,
                   1023:                             struct route_table *rt)
                   1024: {
                   1025:   struct ospf_area *area;
                   1026:   struct ospf_route *or;
                   1027:   struct route_node *rn;
                   1028: 
                   1029:   if (IS_DEBUG_OSPF_EVENT)
                   1030:     zlog_debug ("ospf_abr_process_network_rt(): Start");
                   1031: 
                   1032:   for (rn = route_top (rt); rn; rn = route_next (rn))
                   1033:     {
                   1034:       if ((or = rn->info) == NULL)
                   1035:        continue;
                   1036: 
                   1037:       if (!(area = ospf_area_lookup_by_area_id (ospf, or->u.std.area_id)))
                   1038:        {
                   1039:          if (IS_DEBUG_OSPF_EVENT)
                   1040:            zlog_debug ("ospf_abr_process_network_rt(): area %s no longer exists",
                   1041:                       inet_ntoa (or->u.std.area_id));
                   1042:          continue;
                   1043:        }
                   1044: 
                   1045:       if (IS_DEBUG_OSPF_EVENT)
                   1046:        zlog_debug ("ospf_abr_process_network_rt(): this is a route to %s/%d",
                   1047:                   inet_ntoa (rn->p.u.prefix4), rn->p.prefixlen);
                   1048:       if (or->path_type >= OSPF_PATH_TYPE1_EXTERNAL)
                   1049:        {
                   1050:          if (IS_DEBUG_OSPF_EVENT)
                   1051:            zlog_debug ("ospf_abr_process_network_rt(): "
                   1052:                       "this is an External router, skipping");
                   1053:          continue;
                   1054:        }
                   1055: 
                   1056:       if (or->cost >= OSPF_LS_INFINITY)
                   1057:        {
                   1058:          if (IS_DEBUG_OSPF_EVENT)
                   1059:            zlog_debug ("ospf_abr_process_network_rt():"
                   1060:                       " this route's cost is infinity, skipping");
                   1061:          continue;
                   1062:        }
                   1063: 
                   1064:       if (or->type == OSPF_DESTINATION_DISCARD)
                   1065:        {
                   1066:          if (IS_DEBUG_OSPF_EVENT)
                   1067:            zlog_debug ("ospf_abr_process_network_rt():"
                   1068:                       " this is a discard entry, skipping");
                   1069:          continue;
                   1070:        }
                   1071: 
                   1072:       if (or->path_type == OSPF_PATH_INTRA_AREA &&
                   1073:          !ospf_abr_should_announce (ospf, (struct prefix_ipv4 *) &rn->p, or))
                   1074:        {
                   1075:          if (IS_DEBUG_OSPF_EVENT)
                   1076:            zlog_debug("ospf_abr_process_network_rt(): denied by export-list");
                   1077:          continue;
                   1078:        }
                   1079: 
                   1080:       if (or->path_type == OSPF_PATH_INTRA_AREA &&
                   1081:          !ospf_abr_plist_out_check (area, or, (struct prefix_ipv4 *) &rn->p))
                   1082:        {
                   1083:          if (IS_DEBUG_OSPF_EVENT)
                   1084:            zlog_debug("ospf_abr_process_network_rt(): denied by prefix-list");
                   1085:          continue;
                   1086:        }
                   1087: 
                   1088:       if ((or->path_type == OSPF_PATH_INTER_AREA) &&
                   1089:           !OSPF_IS_AREA_ID_BACKBONE (or->u.std.area_id))
                   1090:        {
                   1091:          if (IS_DEBUG_OSPF_EVENT)
                   1092:            zlog_debug ("ospf_abr_process_network_rt():"
                   1093:                       " this is route is not backbone one, skipping");
                   1094:          continue;
                   1095:        }
                   1096: 
                   1097: 
                   1098:       if ((ospf->abr_type == OSPF_ABR_CISCO) ||
                   1099:           (ospf->abr_type == OSPF_ABR_IBM))
                   1100: 
                   1101:           if (!ospf_act_bb_connection (ospf) &&
                   1102:               or->path_type != OSPF_PATH_INTRA_AREA)
                   1103:             {
                   1104:               if (IS_DEBUG_OSPF_EVENT)
                   1105:                 zlog_debug ("ospf_abr_process_network_rt(): ALT ABR: "
                   1106:                            "No BB connection, skip not intra-area routes");
                   1107:               continue;
                   1108:             }
                   1109: 
                   1110:       if (IS_DEBUG_OSPF_EVENT)
                   1111:        zlog_debug ("ospf_abr_process_network_rt(): announcing");
                   1112:       ospf_abr_announce_network (ospf, (struct prefix_ipv4 *)&rn->p, or);
                   1113:     }
                   1114: 
                   1115:   if (IS_DEBUG_OSPF_EVENT)
                   1116:     zlog_debug ("ospf_abr_process_network_rt(): Stop");
                   1117: }
                   1118: 
                   1119: static void
                   1120: ospf_abr_announce_rtr_to_area (struct prefix_ipv4 *p, u_int32_t cost,
                   1121:                               struct ospf_area *area)
                   1122: {
                   1123:   struct ospf_lsa *lsa, *old = NULL;
                   1124:   struct summary_lsa *slsa = NULL;
                   1125: 
                   1126:   if (IS_DEBUG_OSPF_EVENT)
                   1127:     zlog_debug ("ospf_abr_announce_rtr_to_area(): Start");
                   1128: 
                   1129:   old = ospf_lsa_lookup_by_prefix (area->lsdb, OSPF_ASBR_SUMMARY_LSA,
                   1130:                                   p, area->ospf->router_id);
                   1131:   if (old)
                   1132:     {
                   1133:       if (IS_DEBUG_OSPF_EVENT)
                   1134:        zlog_debug ("ospf_abr_announce_rtr_to_area(): old summary found");
                   1135:       slsa = (struct summary_lsa *) old->data;
                   1136: 
                   1137:       if (IS_DEBUG_OSPF_EVENT)
                   1138:        zlog_debug ("ospf_abr_announce_network_to_area(): "
                   1139:                   "old metric: %d, new metric: %d",
                   1140:                   GET_METRIC (slsa->metric), cost);
                   1141:     }
                   1142: 
1.1.1.3 ! misho    1143:   if (old && (GET_METRIC (slsa->metric) == cost) &&
        !          1144:       ((old->flags & OSPF_LSA_IN_MAXAGE) == 0))
1.1       misho    1145:     {
                   1146:       if (IS_DEBUG_OSPF_EVENT)
                   1147:        zlog_debug ("ospf_abr_announce_rtr_to_area(): old summary approved");
                   1148:       SET_FLAG (old->flags, OSPF_LSA_APPROVED);
                   1149:     }
                   1150:   else
                   1151:     {
                   1152:       if (IS_DEBUG_OSPF_EVENT)
                   1153:        zlog_debug ("ospf_abr_announce_rtr_to_area(): 2.2");
                   1154:        
                   1155:       if (old) 
                   1156:        { 
                   1157:          set_metric (old, cost);
                   1158:          lsa = ospf_lsa_refresh (area->ospf, old);
                   1159:        }
                   1160:       else
                   1161:        lsa = ospf_summary_asbr_lsa_originate (p, cost, area);
                   1162:       if (!lsa)
                   1163:         {
                   1164:           char buf[INET_ADDRSTRLEN + 3]; /* ipv4 and /XX */
                   1165:           
                   1166:           prefix2str ((struct prefix *)p, buf, sizeof(buf));
                   1167:           zlog_warn ("%s: Could not refresh/originate %s to %s",
                   1168:                      __func__,
                   1169:                      buf,
                   1170:                      inet_ntoa (area->area_id));
                   1171:           return;
                   1172:         }
                   1173:       
                   1174:       if (IS_DEBUG_OSPF_EVENT)
                   1175:        zlog_debug ("ospf_abr_announce_rtr_to_area(): "
                   1176:                   "flooding new version of summary");
                   1177: 
                   1178:       /*
                   1179:       zlog_info ("ospf_abr_announce_rtr_to_area(): creating new summary");
                   1180:       lsa = ospf_summary_asbr_lsa (p, cost, area, old); */
                   1181: 
                   1182:       SET_FLAG (lsa->flags, OSPF_LSA_APPROVED);
                   1183:       /* ospf_flood_through_area (area, NULL, lsa);*/
                   1184:     }
                   1185: 
                   1186:   if (IS_DEBUG_OSPF_EVENT)
                   1187:     zlog_debug ("ospf_abr_announce_rtr_to_area(): Stop");
                   1188: }
                   1189: 
                   1190: 
                   1191: static void
                   1192: ospf_abr_announce_rtr (struct ospf *ospf,
                   1193:                       struct prefix_ipv4 *p, struct ospf_route *or)
                   1194: {
                   1195:   struct listnode *node;
                   1196:   struct ospf_area *area;
                   1197: 
                   1198:   if (IS_DEBUG_OSPF_EVENT)
                   1199:     zlog_debug ("ospf_abr_announce_rtr(): Start");
                   1200: 
                   1201:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1202:     {
                   1203:       if (IS_DEBUG_OSPF_EVENT)
                   1204:        zlog_debug ("ospf_abr_announce_rtr(): looking at area %s",
                   1205:                   inet_ntoa (area->area_id));
                   1206: 
                   1207:       if (IPV4_ADDR_SAME (&or->u.std.area_id, &area->area_id))
                   1208:        continue;
                   1209: 
                   1210:       if (ospf_abr_nexthops_belong_to_area (or, area))
                   1211:        continue;
                   1212: 
                   1213:       if (area->external_routing != OSPF_AREA_DEFAULT)
                   1214:        {
                   1215:          if (IS_DEBUG_OSPF_EVENT)
                   1216:            zlog_debug ("ospf_abr_announce_rtr(): "
                   1217:                       "area %s doesn't support external routing",
                   1218:                       inet_ntoa(area->area_id));
                   1219:           continue;
                   1220:        }
                   1221: 
                   1222:       if (or->path_type == OSPF_PATH_INTER_AREA)
                   1223:        {
                   1224:          if (IS_DEBUG_OSPF_EVENT)
                   1225:            zlog_debug ("ospf_abr_announce_rtr(): "
                   1226:                       "this is inter-area route to %s", inet_ntoa (p->prefix));
                   1227:           if (!OSPF_IS_AREA_BACKBONE (area))
                   1228:            ospf_abr_announce_rtr_to_area (p, or->cost, area);
                   1229:        }
                   1230: 
                   1231:       if (or->path_type == OSPF_PATH_INTRA_AREA)
                   1232:        {
                   1233:          if (IS_DEBUG_OSPF_EVENT)
                   1234:            zlog_debug ("ospf_abr_announce_rtr(): "
                   1235:                       "this is intra-area route to %s", inet_ntoa (p->prefix));
                   1236:           ospf_abr_announce_rtr_to_area (p, or->cost, area);
                   1237:        }
                   1238:     }
                   1239: 
                   1240:   if (IS_DEBUG_OSPF_EVENT)
                   1241:     zlog_debug ("ospf_abr_announce_rtr(): Stop");
                   1242: }
                   1243: 
                   1244: static void
                   1245: ospf_abr_process_router_rt (struct ospf *ospf, struct route_table *rt)
                   1246: {
                   1247:   struct ospf_route *or;
                   1248:   struct route_node *rn;
                   1249:   struct list *l;
                   1250: 
                   1251:   if (IS_DEBUG_OSPF_EVENT)
                   1252:     zlog_debug ("ospf_abr_process_router_rt(): Start");
                   1253: 
                   1254:   for (rn = route_top (rt); rn; rn = route_next (rn))
                   1255:     {
                   1256:       struct listnode *node, *nnode;
                   1257:       char flag = 0;
                   1258:       struct ospf_route *best = NULL;
                   1259: 
                   1260:       if (rn->info == NULL)
                   1261:        continue;
                   1262: 
                   1263:       l = rn->info;
                   1264: 
                   1265:       if (IS_DEBUG_OSPF_EVENT)
                   1266:        zlog_debug ("ospf_abr_process_router_rt(): this is a route to %s",
                   1267:                   inet_ntoa (rn->p.u.prefix4));
                   1268: 
                   1269:       for (ALL_LIST_ELEMENTS (l, node, nnode, or))
                   1270:        {
                   1271:          if (!ospf_area_lookup_by_area_id (ospf, or->u.std.area_id))
                   1272:            {
                   1273:              if (IS_DEBUG_OSPF_EVENT)
                   1274:                zlog_debug ("ospf_abr_process_router_rt(): area %s no longer exists",
                   1275:                         inet_ntoa (or->u.std.area_id));
                   1276:              continue;
                   1277:            }
                   1278: 
                   1279: 
                   1280:          if (!CHECK_FLAG (or->u.std.flags, ROUTER_LSA_EXTERNAL))
                   1281:            {
                   1282:              if (IS_DEBUG_OSPF_EVENT)
                   1283:                zlog_debug ("ospf_abr_process_router_rt(): "
                   1284:                           "This is not an ASBR, skipping");
                   1285:              continue;
                   1286:            }
                   1287: 
                   1288:          if (!flag)
                   1289:            {
                   1290:              best = ospf_find_asbr_route (ospf, rt,
                   1291:                                           (struct prefix_ipv4 *) &rn->p);
                   1292:              flag = 1;
                   1293:            }
                   1294:          
                   1295:         if (best == NULL)
                   1296:          continue;
                   1297:        
                   1298:         if (or != best)
                   1299:          {
                   1300:            if (IS_DEBUG_OSPF_EVENT)
                   1301:              zlog_debug ("ospf_abr_process_router_rt(): "
                   1302:                         "This route is not the best among possible, skipping");
                   1303:            continue;
                   1304:          }
                   1305:        
                   1306:         if (or->path_type == OSPF_PATH_INTER_AREA &&
                   1307:             !OSPF_IS_AREA_ID_BACKBONE (or->u.std.area_id))
                   1308:          {
                   1309:            if (IS_DEBUG_OSPF_EVENT)
                   1310:              zlog_debug ("ospf_abr_process_router_rt(): "
                   1311:                         "This route is not a backbone one, skipping");
                   1312:            continue;
                   1313:          }
                   1314: 
                   1315:         if (or->cost >= OSPF_LS_INFINITY)
                   1316:          {
                   1317:            if (IS_DEBUG_OSPF_EVENT)
                   1318:              zlog_debug ("ospf_abr_process_router_rt(): "
                   1319:                         "This route has LS_INFINITY metric, skipping");
                   1320:            continue;
                   1321:          }
                   1322: 
                   1323:         if (ospf->abr_type == OSPF_ABR_CISCO
                   1324:            || ospf->abr_type == OSPF_ABR_IBM)
                   1325:          if (!ospf_act_bb_connection (ospf)
                   1326:              && or->path_type != OSPF_PATH_INTRA_AREA)
                   1327:            {
                   1328:              if (IS_DEBUG_OSPF_EVENT)
                   1329:                zlog_debug("ospf_abr_process_network_rt(): ALT ABR: "
                   1330:                          "No BB connection, skip not intra-area routes");
                   1331:              continue;
                   1332:            }
                   1333: 
                   1334:         ospf_abr_announce_rtr (ospf, (struct prefix_ipv4 *) &rn->p, or);
                   1335: 
                   1336:        }
                   1337: 
                   1338:     }
                   1339: 
                   1340:   if (IS_DEBUG_OSPF_EVENT)
                   1341:     zlog_debug ("ospf_abr_process_router_rt(): Stop");
                   1342: }
                   1343: 
                   1344: static void
                   1345: ospf_abr_unapprove_translates (struct ospf *ospf) /* For NSSA Translations */
                   1346: {
                   1347:   struct ospf_lsa *lsa;
                   1348:   struct route_node *rn;
                   1349: 
                   1350:   if (IS_DEBUG_OSPF_NSSA)
                   1351:     zlog_debug ("ospf_abr_unapprove_translates(): Start");
                   1352: 
                   1353:   /* NSSA Translator is not checked, because it may have gone away,
                   1354:     and we would want to flush any residuals anyway */
                   1355: 
                   1356:   LSDB_LOOP (EXTERNAL_LSDB (ospf), rn, lsa)
                   1357:     if (CHECK_FLAG (lsa->flags, OSPF_LSA_LOCAL_XLT))
                   1358:       {
                   1359:         UNSET_FLAG (lsa->flags, OSPF_LSA_APPROVED);
                   1360:         if (IS_DEBUG_OSPF_NSSA)
                   1361:           zlog_debug ("ospf_abr_unapprove_translates(): "
                   1362:                      "approved unset on link id %s",
                   1363:                      inet_ntoa (lsa->data->id));
                   1364:       }
                   1365: 
                   1366:   if (IS_DEBUG_OSPF_NSSA)
                   1367:     zlog_debug ("ospf_abr_unapprove_translates(): Stop");
                   1368: }
                   1369: 
                   1370: static void
                   1371: ospf_abr_unapprove_summaries (struct ospf *ospf)
                   1372: {
                   1373:   struct listnode *node;
                   1374:   struct ospf_area *area;
                   1375:   struct route_node *rn;
                   1376:   struct ospf_lsa *lsa;
                   1377: 
                   1378:   if (IS_DEBUG_OSPF_EVENT)
                   1379:     zlog_debug ("ospf_abr_unapprove_summaries(): Start");
                   1380: 
                   1381:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1382:     {
                   1383:       if (IS_DEBUG_OSPF_EVENT)
                   1384:         zlog_debug ("ospf_abr_unapprove_summaries(): "
                   1385:                    "considering area %s",
                   1386:                    inet_ntoa (area->area_id)); 
                   1387:       LSDB_LOOP (SUMMARY_LSDB (area), rn, lsa)
                   1388:       if (ospf_lsa_is_self_originated (ospf, lsa))
                   1389:         {
                   1390:           if (IS_DEBUG_OSPF_EVENT)
                   1391:             zlog_debug ("ospf_abr_unapprove_summaries(): "
                   1392:                        "approved unset on summary link id %s",
                   1393:                        inet_ntoa (lsa->data->id)); 
                   1394:           UNSET_FLAG (lsa->flags, OSPF_LSA_APPROVED);
                   1395:         }
                   1396: 
                   1397:       LSDB_LOOP (ASBR_SUMMARY_LSDB (area), rn, lsa)
                   1398:       if (ospf_lsa_is_self_originated (ospf, lsa))
                   1399:         {
                   1400:           if (IS_DEBUG_OSPF_EVENT)
                   1401:             zlog_debug ("ospf_abr_unapprove_summaries(): "
                   1402:                        "approved unset on asbr-summary link id %s",
                   1403:                        inet_ntoa (lsa->data->id));
                   1404:           UNSET_FLAG (lsa->flags, OSPF_LSA_APPROVED);
                   1405:         }
                   1406:     }
                   1407: 
                   1408:   if (IS_DEBUG_OSPF_EVENT)
                   1409:     zlog_debug ("ospf_abr_unapprove_summaries(): Stop");
                   1410: }
                   1411: 
                   1412: static void
                   1413: ospf_abr_prepare_aggregates (struct ospf *ospf)
                   1414: {
                   1415:   struct listnode *node;
                   1416:   struct route_node *rn;
                   1417:   struct ospf_area_range *range;
                   1418:   struct ospf_area *area;
                   1419: 
                   1420:   if (IS_DEBUG_OSPF_EVENT)
                   1421:     zlog_debug ("ospf_abr_prepare_aggregates(): Start");
                   1422: 
                   1423:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1424:     {
                   1425:       for (rn = route_top (area->ranges); rn; rn = route_next (rn))
                   1426:        if ((range = rn->info) != NULL)
                   1427:          {
                   1428:            range->cost = 0;
                   1429:            range->specifics = 0;
                   1430:          }
                   1431:     }
                   1432: 
                   1433:   if (IS_DEBUG_OSPF_EVENT)
                   1434:     zlog_debug ("ospf_abr_prepare_aggregates(): Stop");
                   1435: }
                   1436: 
                   1437: static void
                   1438: ospf_abr_announce_aggregates (struct ospf *ospf)
                   1439: {
                   1440:   struct ospf_area *area, *ar;
                   1441:   struct ospf_area_range *range;
                   1442:   struct route_node *rn;
                   1443:   struct prefix p;
                   1444:   struct listnode *node, *n;
                   1445: 
                   1446:   if (IS_DEBUG_OSPF_EVENT)
                   1447:     zlog_debug ("ospf_abr_announce_aggregates(): Start");
                   1448: 
                   1449:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1450:     {
                   1451:       if (IS_DEBUG_OSPF_EVENT)
                   1452:        zlog_debug ("ospf_abr_announce_aggregates(): looking at area %s",
                   1453:                   inet_ntoa (area->area_id));
                   1454: 
                   1455:       for (rn = route_top (area->ranges); rn; rn = route_next (rn))
                   1456:        if ((range =  rn->info))
                   1457:          {
                   1458:            if (!CHECK_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE))
                   1459:              {
                   1460:                if (IS_DEBUG_OSPF_EVENT)
                   1461:                  zlog_debug ("ospf_abr_announce_aggregates():"
                   1462:                             " discarding suppress-ranges");
                   1463:                continue;
                   1464:              }
                   1465: 
                   1466:            p.family = AF_INET;
                   1467:            p.u.prefix4 = range->addr;
                   1468:            p.prefixlen = range->masklen;
                   1469: 
                   1470:            if (IS_DEBUG_OSPF_EVENT)
                   1471:              zlog_debug ("ospf_abr_announce_aggregates():"
                   1472:                         " this is range: %s/%d",
                   1473:                         inet_ntoa (p.u.prefix4), p.prefixlen);
                   1474: 
                   1475:            if (CHECK_FLAG (range->flags, OSPF_AREA_RANGE_SUBSTITUTE))
                   1476:              {
                   1477:                p.family = AF_INET;
                   1478:                p.u.prefix4 = range->subst_addr;
                   1479:                p.prefixlen = range->subst_masklen;
                   1480:              }
                   1481: 
                   1482:            if (range->specifics)
                   1483:              {
                   1484:                if (IS_DEBUG_OSPF_EVENT)
                   1485:                  zlog_debug ("ospf_abr_announce_aggregates(): active range");
                   1486: 
                   1487:                for (ALL_LIST_ELEMENTS_RO (ospf->areas, n, ar))
                   1488:                  {
                   1489:                    if (ar == area)
                   1490:                      continue;
                   1491: 
                   1492:                    /* We do not check nexthops here, because
                   1493:                       intra-area routes can be associated with
                   1494:                       one area only */
                   1495: 
                   1496:                    /* backbone routes are not summarized
                   1497:                       when announced into transit areas */
                   1498: 
                   1499:                    if (ospf_area_is_transit (ar) &&
                   1500:                        OSPF_IS_AREA_BACKBONE (area))
                   1501:                      {
                   1502:                        if (IS_DEBUG_OSPF_EVENT)
                   1503:                          zlog_debug ("ospf_abr_announce_aggregates(): Skipping "
                   1504:                                     "announcement of BB aggregate into"
                   1505:                                     " a transit area");
                   1506:                        continue; 
                   1507:                      }
                   1508:                    ospf_abr_announce_network_to_area ((struct prefix_ipv4 *)&p, range->cost, ar);
                   1509:                  }
                   1510:              }
                   1511:          }
                   1512:     }
                   1513: 
                   1514:   if (IS_DEBUG_OSPF_EVENT)
                   1515:     zlog_debug ("ospf_abr_announce_aggregates(): Stop");
                   1516: }
                   1517: 
                   1518: static void
                   1519: ospf_abr_send_nssa_aggregates (struct ospf *ospf) /* temporarily turned off */
                   1520: {
                   1521:   struct listnode *node; /*, n; */
                   1522:   struct ospf_area *area; /*, *ar; */
                   1523:   struct route_node *rn;
                   1524:   struct ospf_area_range *range;
                   1525:   struct prefix_ipv4 p;
                   1526: 
                   1527:   if (IS_DEBUG_OSPF_NSSA)
                   1528:     zlog_debug ("ospf_abr_send_nssa_aggregates(): Start");
                   1529: 
                   1530:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1531:     {
                   1532:       if (! area->NSSATranslatorState)
                   1533:        continue;
                   1534: 
                   1535:       if (IS_DEBUG_OSPF_NSSA)
                   1536:        zlog_debug ("ospf_abr_send_nssa_aggregates(): looking at area %s",
                   1537:                   inet_ntoa (area->area_id));
                   1538: 
                   1539:       for (rn = route_top (area->ranges); rn; rn = route_next (rn))
                   1540:        {
                   1541:           if (rn->info == NULL)
                   1542:            continue;
                   1543: 
                   1544:          range = rn->info;
                   1545: 
                   1546:           if (!CHECK_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE))
                   1547:            {
                   1548:              if (IS_DEBUG_OSPF_NSSA)
                   1549:                zlog_debug ("ospf_abr_send_nssa_aggregates():"
                   1550:                           " discarding suppress-ranges");
                   1551:              continue;
                   1552:            }
                   1553: 
                   1554:           p.family = AF_INET;
                   1555:           p.prefix = range->addr;
                   1556:           p.prefixlen = range->masklen;
                   1557: 
                   1558:          if (IS_DEBUG_OSPF_NSSA)
                   1559:            zlog_debug ("ospf_abr_send_nssa_aggregates():"
                   1560:                       " this is range: %s/%d",
                   1561:                       inet_ntoa (p.prefix), p.prefixlen);
                   1562: 
                   1563:           if (CHECK_FLAG (range->flags, OSPF_AREA_RANGE_SUBSTITUTE))
                   1564:            {
                   1565:              p.family = AF_INET;
                   1566:              p.prefix = range->subst_addr;
                   1567:              p.prefixlen = range->subst_masklen;
                   1568:            }
                   1569: 
                   1570:           if (range->specifics)
                   1571:             {
                   1572:               if (IS_DEBUG_OSPF_NSSA)
                   1573:                 zlog_debug ("ospf_abr_send_nssa_aggregates(): active range");
                   1574: 
                   1575:               /* Fetch LSA-Type-7 from aggregate prefix, and then
                   1576:                *  translate, Install (as Type-5), Approve, and Flood
                   1577:                */
                   1578:               ospf_abr_translate_nssa_range (&p, range->cost);
                   1579:             }
                   1580:         } /* all area ranges*/
                   1581:     } /* all areas */
                   1582: 
                   1583:   if (IS_DEBUG_OSPF_NSSA)
                   1584:     zlog_debug ("ospf_abr_send_nssa_aggregates(): Stop");
                   1585: }
                   1586: 
                   1587: static void
                   1588: ospf_abr_announce_stub_defaults (struct ospf *ospf)
                   1589: {
                   1590:   struct listnode *node;
                   1591:   struct ospf_area *area;
                   1592:   struct prefix_ipv4 p;
                   1593: 
                   1594:   if (! IS_OSPF_ABR (ospf))
                   1595:     return;
                   1596: 
                   1597:   if (IS_DEBUG_OSPF_EVENT)
                   1598:     zlog_debug ("ospf_abr_announce_stub_defaults(): Start");
                   1599: 
                   1600:   p.family = AF_INET;
                   1601:   p.prefix.s_addr = OSPF_DEFAULT_DESTINATION;
                   1602:   p.prefixlen = 0;
                   1603: 
                   1604:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1605:     {
                   1606:       if (IS_DEBUG_OSPF_EVENT)
                   1607:         zlog_debug ("ospf_abr_announce_stub_defaults(): looking at area %s",
                   1608:                    inet_ntoa (area->area_id));
                   1609: 
                   1610:      if ( (area->external_routing != OSPF_AREA_STUB)
                   1611:           && (area->external_routing != OSPF_AREA_NSSA)
                   1612:         )
                   1613:        continue;
                   1614: 
                   1615:       if (OSPF_IS_AREA_BACKBONE (area))
                   1616:         continue; /* Sanity Check */
                   1617: 
                   1618:       if (IS_DEBUG_OSPF_EVENT)
                   1619:         zlog_debug ("ospf_abr_announce_stub_defaults(): "
                   1620:                    "announcing 0.0.0.0/0 to area %s",
                   1621:                  inet_ntoa (area->area_id));
                   1622:       ospf_abr_announce_network_to_area (&p, area->default_cost, area);
                   1623:     }
                   1624: 
                   1625:   if (IS_DEBUG_OSPF_EVENT)
                   1626:     zlog_debug ("ospf_abr_announce_stub_defaults(): Stop");
                   1627: }
                   1628: 
                   1629: static int
                   1630: ospf_abr_remove_unapproved_translates_apply (struct ospf *ospf,
                   1631:                                             struct ospf_lsa *lsa)
                   1632: {
                   1633:   if (CHECK_FLAG (lsa->flags, OSPF_LSA_LOCAL_XLT)
                   1634:       && ! CHECK_FLAG (lsa->flags, OSPF_LSA_APPROVED))
                   1635:     {
                   1636:       zlog_info ("ospf_abr_remove_unapproved_translates(): "
                   1637:                 "removing unapproved translates, ID: %s",
                   1638:                 inet_ntoa (lsa->data->id));
                   1639: 
                   1640:       /* FLUSH THROUGHOUT AS */
                   1641:       ospf_lsa_flush_as (ospf, lsa);
                   1642: 
                   1643:       /* DISCARD from LSDB  */
                   1644:     }
                   1645:   return 0;
                   1646: }
                   1647: 
                   1648: static void
                   1649: ospf_abr_remove_unapproved_translates (struct ospf *ospf)
                   1650: {
                   1651:   struct route_node *rn;
                   1652:   struct ospf_lsa *lsa;
                   1653: 
                   1654:   /* All AREA PROCESS should have APPROVED necessary LSAs */
                   1655:   /* Remove any left over and not APPROVED */
                   1656:   if (IS_DEBUG_OSPF_NSSA)
                   1657:     zlog_debug ("ospf_abr_remove_unapproved_translates(): Start");
                   1658: 
                   1659:   LSDB_LOOP (EXTERNAL_LSDB (ospf), rn, lsa)
                   1660:     ospf_abr_remove_unapproved_translates_apply (ospf, lsa);
                   1661:  
                   1662:   if (IS_DEBUG_OSPF_NSSA)
                   1663:     zlog_debug ("ospf_abr_remove_unapproved_translates(): Stop");
                   1664: }
                   1665: 
                   1666: static void
                   1667: ospf_abr_remove_unapproved_summaries (struct ospf *ospf)
                   1668: {
                   1669:   struct listnode *node;
                   1670:   struct ospf_area *area;
                   1671:   struct route_node *rn;
                   1672:   struct ospf_lsa *lsa;
                   1673: 
                   1674:   if (IS_DEBUG_OSPF_EVENT)
                   1675:     zlog_debug ("ospf_abr_remove_unapproved_summaries(): Start");
                   1676: 
                   1677:   for (ALL_LIST_ELEMENTS_RO (ospf->areas, node, area))
                   1678:     {
                   1679:       if (IS_DEBUG_OSPF_EVENT)
                   1680:        zlog_debug ("ospf_abr_remove_unapproved_summaries(): "
                   1681:                   "looking at area %s", inet_ntoa (area->area_id));
                   1682: 
                   1683:       LSDB_LOOP (SUMMARY_LSDB (area), rn, lsa)
                   1684:        if (ospf_lsa_is_self_originated (ospf, lsa))
                   1685:          if (!CHECK_FLAG (lsa->flags, OSPF_LSA_APPROVED))
                   1686:            ospf_lsa_flush_area (lsa, area);
                   1687: 
                   1688:       LSDB_LOOP (ASBR_SUMMARY_LSDB (area), rn, lsa)
                   1689:        if (ospf_lsa_is_self_originated (ospf, lsa))
                   1690:          if (!CHECK_FLAG (lsa->flags, OSPF_LSA_APPROVED))
                   1691:            ospf_lsa_flush_area (lsa, area);
                   1692:     }
                   1693:  
                   1694:   if (IS_DEBUG_OSPF_EVENT)
                   1695:     zlog_debug ("ospf_abr_remove_unapproved_summaries(): Stop");
                   1696: }
                   1697: 
                   1698: static void
                   1699: ospf_abr_manage_discard_routes (struct ospf *ospf)
                   1700: {
                   1701:   struct listnode *node, *nnode;
                   1702:   struct route_node *rn;
                   1703:   struct ospf_area *area;
                   1704:   struct ospf_area_range *range;
                   1705: 
                   1706:   for (ALL_LIST_ELEMENTS (ospf->areas, node, nnode, area))
                   1707:     for (rn = route_top (area->ranges); rn; rn = route_next (rn))
                   1708:       if ((range = rn->info) != NULL)
                   1709:        if (CHECK_FLAG (range->flags, OSPF_AREA_RANGE_ADVERTISE))
                   1710:          {
                   1711:            if (range->specifics)
                   1712:              ospf_add_discard_route (ospf->new_table, area,
                   1713:                                      (struct prefix_ipv4 *) &rn->p);
                   1714:            else
1.1.1.3 ! misho    1715:              ospf_delete_discard_route (ospf->new_table,
        !          1716:                                         (struct prefix_ipv4 *) &rn->p);
1.1       misho    1717:          }
                   1718: }
                   1719: 
                   1720: /* This is the function taking care about ABR NSSA, i.e.  NSSA
                   1721:    Translator, -LSA aggregation and flooding. For all NSSAs
                   1722: 
                   1723:    Any SELF-AS-LSA is in the Type-5 LSDB and Type-7 LSDB.  These LSA's
                   1724:    are refreshed from the Type-5 LSDB, installed into the Type-7 LSDB
                   1725:    with the P-bit set.
                   1726: 
                   1727:    Any received Type-5s are legal for an ABR, else illegal for IR.
                   1728:    Received Type-7s are installed, by area, with incoming P-bit.  They
                   1729:    are flooded; if the Elected NSSA Translator, then P-bit off.
                   1730: 
                   1731:    Additionally, this ABR will place "translated type-7's" into the
                   1732:    Type-5 LSDB in order to keep track of APPROVAL or not.
                   1733: 
                   1734:    It will scan through every area, looking for Type-7 LSAs with P-Bit
                   1735:    SET. The Type-7's are either AS-FLOODED & 5-INSTALLED or
                   1736:    AGGREGATED.  Later, the AGGREGATED LSAs are AS-FLOODED &
                   1737:    5-INSTALLED.
                   1738: 
                   1739:    5-INSTALLED is into the Type-5 LSDB; Any UNAPPROVED Type-5 LSAs
                   1740:    left over are FLUSHED and DISCARDED.
                   1741: 
                   1742:    For External Calculations, any NSSA areas use the Type-7 AREA-LSDB,
                   1743:    any ABR-non-NSSA areas use the Type-5 GLOBAL-LSDB. */
                   1744: 
                   1745: static void
                   1746: ospf_abr_nssa_task (struct ospf *ospf) /* called only if any_nssa */
                   1747: {
                   1748:   if (IS_DEBUG_OSPF_NSSA)
                   1749:     zlog_debug ("Check for NSSA-ABR Tasks():");
                   1750: 
                   1751:   if (! IS_OSPF_ABR (ospf))
                   1752:     return;
                   1753: 
                   1754:   if (! ospf->anyNSSA)
                   1755:     return;
                   1756: 
                   1757:   /* Each area must confirm TranslatorRole */
                   1758:   if (IS_DEBUG_OSPF_NSSA)
                   1759:     zlog_debug ("ospf_abr_nssa_task(): Start");
                   1760: 
                   1761:   /* For all Global Entries flagged "local-translate", unset APPROVED */
                   1762:   if (IS_DEBUG_OSPF_NSSA)
                   1763:     zlog_debug ("ospf_abr_nssa_task(): unapprove translates");
                   1764: 
                   1765:   ospf_abr_unapprove_translates (ospf);
                   1766: 
                   1767:   /* RESET all Ranges in every Area, same as summaries */
                   1768:   if (IS_DEBUG_OSPF_NSSA)
                   1769:     zlog_debug ("ospf_abr_nssa_task(): NSSA initialize aggregates");
                   1770:   ospf_abr_prepare_aggregates (ospf);  /*TURNED OFF just for now */
                   1771: 
                   1772:   /* For all NSSAs, Type-7s, translate to 5's, INSTALL/FLOOD, or
                   1773:    *  Aggregate as Type-7
                   1774:    * Install or Approve in Type-5 Global LSDB 
                   1775:    */
                   1776:   if (IS_DEBUG_OSPF_NSSA)
                   1777:     zlog_debug ("ospf_abr_nssa_task(): process translates");
                   1778:   ospf_abr_process_nssa_translates (ospf);
                   1779: 
                   1780:   /* Translate/Send any "ranged" aggregates, and also 5-Install and
                   1781:    *  Approve
                   1782:    * Scan Type-7's for aggregates, translate to Type-5's,
                   1783:    *  Install/Flood/Approve 
                   1784:    */
                   1785:   if (IS_DEBUG_OSPF_NSSA)
                   1786:     zlog_debug("ospf_abr_nssa_task(): send NSSA aggregates");
                   1787:   ospf_abr_send_nssa_aggregates (ospf);  /*TURNED OFF FOR NOW */
                   1788: 
                   1789:   /* Send any NSSA defaults as Type-5 
                   1790:    *if (IS_DEBUG_OSPF_NSSA)
                   1791:    * zlog_debug ("ospf_abr_nssa_task(): announce nssa defaults");
                   1792:    *ospf_abr_announce_nssa_defaults (ospf);
                   1793:    * havnt a clue what above is supposed to do.
                   1794:    */
                   1795:    
                   1796:   /* Flush any unapproved previous translates from Global Data Base */
                   1797:   if (IS_DEBUG_OSPF_NSSA)
                   1798:     zlog_debug ("ospf_abr_nssa_task(): remove unapproved translates");
                   1799:   ospf_abr_remove_unapproved_translates (ospf);
                   1800: 
                   1801:   ospf_abr_manage_discard_routes (ospf); /* same as normal...discard */
                   1802: 
                   1803:   if (IS_DEBUG_OSPF_NSSA)
                   1804:     zlog_debug ("ospf_abr_nssa_task(): Stop");
                   1805: }
                   1806: 
                   1807: /* This is the function taking care about ABR stuff, i.e.
                   1808:    summary-LSA origination and flooding. */
                   1809: void
                   1810: ospf_abr_task (struct ospf *ospf)
                   1811: {
                   1812:   if (IS_DEBUG_OSPF_EVENT)
                   1813:     zlog_debug ("ospf_abr_task(): Start");
                   1814: 
                   1815:   if (ospf->new_table == NULL || ospf->new_rtrs == NULL)
                   1816:     {
                   1817:       if (IS_DEBUG_OSPF_EVENT)
                   1818:        zlog_debug ("ospf_abr_task(): Routing tables are not yet ready");
                   1819:       return;
                   1820:     }
                   1821: 
                   1822:   if (IS_DEBUG_OSPF_EVENT)
                   1823:     zlog_debug ("ospf_abr_task(): unapprove summaries");
                   1824:   ospf_abr_unapprove_summaries (ospf);
                   1825: 
                   1826:   if (IS_DEBUG_OSPF_EVENT)
                   1827:     zlog_debug ("ospf_abr_task(): prepare aggregates");
                   1828:   ospf_abr_prepare_aggregates (ospf);
                   1829: 
                   1830:   if (IS_OSPF_ABR (ospf))
                   1831:     {
                   1832:       if (IS_DEBUG_OSPF_EVENT)
                   1833:        zlog_debug ("ospf_abr_task(): process network RT");
                   1834:       ospf_abr_process_network_rt (ospf, ospf->new_table);
                   1835: 
                   1836:       if (IS_DEBUG_OSPF_EVENT)
                   1837:        zlog_debug ("ospf_abr_task(): process router RT");
                   1838:       ospf_abr_process_router_rt (ospf, ospf->new_rtrs);
                   1839: 
                   1840:       if (IS_DEBUG_OSPF_EVENT)
                   1841:        zlog_debug ("ospf_abr_task(): announce aggregates");
                   1842:       ospf_abr_announce_aggregates (ospf);
                   1843: 
                   1844:       if (IS_DEBUG_OSPF_EVENT)
                   1845:        zlog_debug ("ospf_abr_task(): announce stub defaults");
                   1846:       ospf_abr_announce_stub_defaults (ospf);
                   1847:     }
                   1848: 
                   1849:   if (IS_DEBUG_OSPF_EVENT)
                   1850:     zlog_debug ("ospf_abr_task(): remove unapproved summaries");
                   1851:   ospf_abr_remove_unapproved_summaries (ospf);
                   1852: 
                   1853:   ospf_abr_manage_discard_routes (ospf);
                   1854: 
                   1855:   if (IS_DEBUG_OSPF_EVENT)
                   1856:     zlog_debug ("ospf_abr_task(): Stop");
                   1857: }
                   1858: 
                   1859: static int
                   1860: ospf_abr_task_timer (struct thread *thread)
                   1861: {
                   1862:   struct ospf *ospf = THREAD_ARG (thread);
                   1863: 
                   1864:   ospf->t_abr_task = 0;
                   1865: 
                   1866:   if (IS_DEBUG_OSPF_EVENT)
                   1867:     zlog_debug ("Running ABR task on timer");
                   1868: 
                   1869:   ospf_check_abr_status (ospf);
                   1870:   ospf_abr_nssa_check_status (ospf);
                   1871: 
                   1872:   ospf_abr_task (ospf);
                   1873:   ospf_abr_nssa_task (ospf); /* if nssa-abr, then scan Type-7 LSDB */
                   1874: 
                   1875:   return 0;
                   1876: }
                   1877: 
                   1878: void
                   1879: ospf_schedule_abr_task (struct ospf *ospf)
                   1880: {
                   1881:   if (IS_DEBUG_OSPF_EVENT)
                   1882:     zlog_debug ("Scheduling ABR task");
                   1883: 
                   1884:   if (ospf->t_abr_task == NULL)
                   1885:     ospf->t_abr_task = thread_add_timer (master, ospf_abr_task_timer,
                   1886:                                         ospf, OSPF_ABR_TASK_DELAY);
                   1887: }

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