⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ospf6_intra.c

📁 linux 路由软件 可支持RIP OSPF BGP等
💻 C
📖 第 1 页 / 共 3 页
字号:
/* * Copyright (C) 2003 Yasuhiro Ohara * * This file is part of GNU Zebra. * * GNU Zebra is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 2, or (at your option) any * later version. * * GNU Zebra is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNU Zebra; see the file COPYING.  If not, write to the  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,  * Boston, MA 02111-1307, USA.   */#include <zebra.h>#include "log.h"#include "linklist.h"#include "thread.h"#include "memory.h"#include "if.h"#include "prefix.h"#include "table.h"#include "vty.h"#include "command.h"#include "ospf6_proto.h"#include "ospf6_message.h"#include "ospf6_route.h"#include "ospf6_lsa.h"#include "ospf6_lsdb.h"#include "ospf6_top.h"#include "ospf6_area.h"#include "ospf6_interface.h"#include "ospf6_neighbor.h"#include "ospf6_intra.h"#include "ospf6_asbr.h"#include "ospf6_abr.h"#include "ospf6_flood.h"#include "ospf6d.h"/******************************//* RFC2740 3.4.3.1 Router-LSA *//******************************/intospf6_router_lsa_show (struct vty *vty, struct ospf6_lsa *lsa){  char *start, *end, *current;  char buf[32], name[32], bits[16], options[32];  struct ospf6_router_lsa *router_lsa;  struct ospf6_router_lsdesc *lsdesc;  router_lsa = (struct ospf6_router_lsa *)    ((char *) lsa->header + sizeof (struct ospf6_lsa_header));  ospf6_capability_printbuf (router_lsa->bits, bits, sizeof (bits));  ospf6_options_printbuf (router_lsa->options, options, sizeof (options));  vty_out (vty, "    Bits: %s Options: %s%s", bits, options, VNL);  start = (char *) router_lsa + sizeof (struct ospf6_router_lsa);  end = (char *) lsa->header + ntohs (lsa->header->length);  for (current = start; current + sizeof (struct ospf6_router_lsdesc) <= end;       current += sizeof (struct ospf6_router_lsdesc))    {      lsdesc = (struct ospf6_router_lsdesc *) current;      if (lsdesc->type == OSPF6_ROUTER_LSDESC_POINTTOPOINT)        snprintf (name, sizeof (name), "Point-To-Point");      else if (lsdesc->type == OSPF6_ROUTER_LSDESC_TRANSIT_NETWORK)        snprintf (name, sizeof (name), "Transit-Network");      else if (lsdesc->type == OSPF6_ROUTER_LSDESC_STUB_NETWORK)        snprintf (name, sizeof (name), "Stub-Network");      else if (lsdesc->type == OSPF6_ROUTER_LSDESC_VIRTUAL_LINK)        snprintf (name, sizeof (name), "Virtual-Link");      else        snprintf (name, sizeof (name), "Unknown (%#x)", lsdesc->type);      vty_out (vty, "    Type: %s Metric: %d%s",               name, ntohs (lsdesc->metric), VNL);      vty_out (vty, "    Interface ID: %s%s",               inet_ntop (AF_INET, &lsdesc->interface_id,                          buf, sizeof (buf)), VNL);      vty_out (vty, "    Neighbor Interface ID: %s%s",               inet_ntop (AF_INET, &lsdesc->neighbor_interface_id,                          buf, sizeof (buf)), VNL);      vty_out (vty, "    Neighbor Router ID: %s%s",               inet_ntop (AF_INET, &lsdesc->neighbor_router_id,                          buf, sizeof (buf)), VNL);    }  return 0;}intospf6_router_lsa_originate (struct thread *thread){  struct ospf6_area *oa;  char buffer [OSPF6_MAX_LSASIZE];  struct ospf6_lsa_header *lsa_header;  struct ospf6_lsa *lsa;  u_int32_t link_state_id = 0;  listnode i, j;  struct ospf6_interface *oi;  struct ospf6_neighbor *on, *drouter = NULL;  struct ospf6_router_lsa *router_lsa;  struct ospf6_router_lsdesc *lsdesc;  u_int16_t type;  u_int32_t router;  int count;  oa = (struct ospf6_area *) THREAD_ARG (thread);  oa->thread_router_lsa = NULL;  if (IS_OSPF6_DEBUG_ORIGINATE (ROUTER))    zlog_info ("Originate Router-LSA for Area %s", oa->name);  memset (buffer, 0, sizeof (buffer));  lsa_header = (struct ospf6_lsa_header *) buffer;  router_lsa = (struct ospf6_router_lsa *)    ((caddr_t) lsa_header + sizeof (struct ospf6_lsa_header));  OSPF6_OPT_SET (router_lsa->options, OSPF6_OPT_V6);  OSPF6_OPT_SET (router_lsa->options, OSPF6_OPT_E);  OSPF6_OPT_CLEAR (router_lsa->options, OSPF6_OPT_MC);  OSPF6_OPT_CLEAR (router_lsa->options, OSPF6_OPT_N);  OSPF6_OPT_SET (router_lsa->options, OSPF6_OPT_R);  OSPF6_OPT_CLEAR (router_lsa->options, OSPF6_OPT_DC);  if (ospf6_is_router_abr (ospf6))    SET_FLAG (router_lsa->bits, OSPF6_ROUTER_BIT_B);  else    UNSET_FLAG (router_lsa->bits, OSPF6_ROUTER_BIT_B);  if (ospf6_asbr_is_asbr (ospf6))    SET_FLAG (router_lsa->bits, OSPF6_ROUTER_BIT_E);  else    UNSET_FLAG (router_lsa->bits, OSPF6_ROUTER_BIT_E);  UNSET_FLAG (router_lsa->bits, OSPF6_ROUTER_BIT_V);  UNSET_FLAG (router_lsa->bits, OSPF6_ROUTER_BIT_W);  /* describe links for each interfaces */  lsdesc = (struct ospf6_router_lsdesc *)    ((caddr_t) router_lsa + sizeof (struct ospf6_router_lsa));  for (i = listhead (oa->if_list); i; nextnode (i))    {      oi = (struct ospf6_interface *) getdata (i);      /* Interfaces in state Down or Loopback are not described */      if (oi->state == OSPF6_INTERFACE_DOWN ||          oi->state == OSPF6_INTERFACE_LOOPBACK)        continue;      /* Nor are interfaces without any full adjacencies described */      count = 0;      for (j = listhead (oi->neighbor_list); j; nextnode (j))        {          on = (struct ospf6_neighbor *) getdata (j);          if (on->state == OSPF6_NEIGHBOR_FULL)            count++;        }      if (count == 0)        continue;      /* Multiple Router-LSA instance according to size limit setting */      if (oa->router_lsa_size_limit != 0 &&          (caddr_t) lsdesc + sizeof (struct ospf6_router_lsdesc) -          (caddr_t) buffer > oa->router_lsa_size_limit)        {          if ((caddr_t) lsdesc == (caddr_t) router_lsa +                                  sizeof (struct ospf6_router_lsa))            {              if (IS_OSPF6_DEBUG_ORIGINATE (ROUTER))                zlog_info ("Size limit setting for Router-LSA too short");              return 0;            }          /* Fill LSA Header */          lsa_header->age = 0;          lsa_header->type = htons (OSPF6_LSTYPE_ROUTER);          lsa_header->id = htonl (link_state_id);          lsa_header->adv_router = oa->ospf6->router_id;          lsa_header->seqnum =            ospf6_new_ls_seqnum (lsa_header->type, lsa_header->id,                                 lsa_header->adv_router, oa->lsdb);          lsa_header->length = htons ((caddr_t) lsdesc - (caddr_t) buffer);          /* LSA checksum */          ospf6_lsa_checksum (lsa_header);          /* create LSA */          lsa = ospf6_lsa_create (lsa_header);          /* Originate */          ospf6_lsa_originate_area (lsa, oa);          /* Reset setting for consecutive origination */          memset ((caddr_t) router_lsa + sizeof (struct ospf6_router_lsa),                  0, (caddr_t) lsdesc - (caddr_t) router_lsa);          lsdesc = (struct ospf6_router_lsdesc *)            ((caddr_t) router_lsa + sizeof (struct ospf6_router_lsa));          link_state_id ++;        }      /* Point-to-Point interfaces */      if (if_is_pointopoint (oi->interface))        {          for (j = listhead (oi->neighbor_list); j; nextnode (j))            {              on = (struct ospf6_neighbor *) getdata (j);              if (on->state != OSPF6_NEIGHBOR_FULL)                continue;              lsdesc->type = OSPF6_ROUTER_LSDESC_POINTTOPOINT;              lsdesc->metric = htons (oi->cost);              lsdesc->interface_id = htonl (oi->interface->ifindex);              lsdesc->neighbor_interface_id = htonl (on->ifindex);              lsdesc->neighbor_router_id = on->router_id;              lsdesc++;            }        }      /* Broadcast and NBMA interfaces */      if (if_is_broadcast (oi->interface))        {          /* If this router is not DR,             and If this router not fully adjacent with DR,             this interface is not transit yet: ignore. */          if (oi->state != OSPF6_INTERFACE_DR)            {              drouter = ospf6_neighbor_lookup (oi->drouter, oi);              if (drouter == NULL || drouter->state != OSPF6_NEIGHBOR_FULL)                continue;            }          lsdesc->type = OSPF6_ROUTER_LSDESC_TRANSIT_NETWORK;          lsdesc->metric = htons (oi->cost);          lsdesc->interface_id = htonl (oi->interface->ifindex);          if (oi->state != OSPF6_INTERFACE_DR)            {              lsdesc->neighbor_interface_id = htonl (drouter->ifindex);              lsdesc->neighbor_router_id = drouter->router_id;            }          else            {              lsdesc->neighbor_interface_id = htonl (oi->interface->ifindex);              lsdesc->neighbor_router_id = oi->area->ospf6->router_id;            }          lsdesc++;        }      /* Virtual links */        /* xxx */      /* Point-to-Multipoint interfaces */        /* xxx */    }  if ((caddr_t) lsdesc != (caddr_t) router_lsa +                          sizeof (struct ospf6_router_lsa))    {      /* Fill LSA Header */      lsa_header->age = 0;      lsa_header->type = htons (OSPF6_LSTYPE_ROUTER);      lsa_header->id = htonl (link_state_id);      lsa_header->adv_router = oa->ospf6->router_id;      lsa_header->seqnum =        ospf6_new_ls_seqnum (lsa_header->type, lsa_header->id,                             lsa_header->adv_router, oa->lsdb);      lsa_header->length = htons ((caddr_t) lsdesc - (caddr_t) buffer);      /* LSA checksum */      ospf6_lsa_checksum (lsa_header);      /* create LSA */      lsa = ospf6_lsa_create (lsa_header);      /* Originate */      ospf6_lsa_originate_area (lsa, oa);      link_state_id ++;    }  else    {      if (IS_OSPF6_DEBUG_ORIGINATE (ROUTER))        zlog_info ("Nothing to describe in Router-LSA, suppress");    }  /* Do premature-aging of rest, undesired Router-LSAs */  type = ntohs (OSPF6_LSTYPE_ROUTER);  router = oa->ospf6->router_id;  for (lsa = ospf6_lsdb_type_router_head (type, router, oa->lsdb); lsa;       lsa = ospf6_lsdb_type_router_next (type, router, lsa))    {      if (ntohl (lsa->header->id) < link_state_id)        continue;      ospf6_lsa_purge (lsa);    }  return 0;}/*******************************//* RFC2740 3.4.3.2 Network-LSA *//*******************************/intospf6_network_lsa_show (struct vty *vty, struct ospf6_lsa *lsa){  char *start, *end, *current;  struct ospf6_network_lsa *network_lsa;  struct ospf6_network_lsdesc *lsdesc;  char buf[128], options[32];  network_lsa = (struct ospf6_network_lsa *)    ((caddr_t) lsa->header + sizeof (struct ospf6_lsa_header));  ospf6_options_printbuf (network_lsa->options, options, sizeof (options));  vty_out (vty, "     Options: %s%s", options, VNL);  start = (char *) network_lsa + sizeof (struct ospf6_network_lsa);  end = (char *) lsa->header + ntohs (lsa->header->length);  for (current = start; current + sizeof (struct ospf6_network_lsdesc) <= end;       current += sizeof (struct ospf6_network_lsdesc))    {      lsdesc = (struct ospf6_network_lsdesc *) current;      inet_ntop (AF_INET, &lsdesc->router_id, buf, sizeof (buf));      vty_out (vty, "     Attached Router: %s%s", buf, VNL);    }  return 0;}intospf6_network_lsa_originate (struct thread *thread){  struct ospf6_interface *oi;  char buffer [OSPF6_MAX_LSASIZE];  struct ospf6_lsa_header *lsa_header;  int count;  struct ospf6_lsa *old, *lsa;  struct ospf6_network_lsa *network_lsa;  struct ospf6_network_lsdesc *lsdesc;  struct ospf6_neighbor *on;  struct ospf6_link_lsa *link_lsa;  listnode i;  u_int16_t type;  oi = (struct ospf6_interface *) THREAD_ARG (thread);  oi->thread_network_lsa = NULL;  /* The interface must be enabled until here. A Network-LSA of a     disabled interface (but was once enabled) should be flushed     by ospf6_lsa_refresh (), and does not come here. */  assert (oi->area);  old = ospf6_lsdb_lookup (htons (OSPF6_LSTYPE_NETWORK),                           htonl (oi->interface->ifindex),                           oi->area->ospf6->router_id, oi->area->lsdb);  /* Do not originate Network-LSA if not DR */  if (oi->state != OSPF6_INTERFACE_DR)    {      if (old)        ospf6_lsa_purge (old);      return 0;    }  if (IS_OSPF6_DEBUG_ORIGINATE (NETWORK))    zlog_info ("Originate Network-LSA for Interface %s", oi->interface->name);  /* If none of neighbor is adjacent to us */  count = 0;  for (i = listhead (oi->neighbor_list); i; nextnode (i))    {      on = (struct ospf6_neighbor *) getdata (i);      if (on->state == OSPF6_NEIGHBOR_FULL)        count++;    }  if (count == 0)    {      if (IS_OSPF6_DEBUG_ORIGINATE (NETWORK))        zlog_info ("Interface stub, ignore");      if (old)        ospf6_lsa_purge (old);      return 0;    }  /* prepare buffer */  memset (buffer, 0, sizeof (buffer));  lsa_header = (struct ospf6_lsa_header *) buffer;  network_lsa = (struct ospf6_network_lsa *)    ((caddr_t) lsa_header + sizeof (struct ospf6_lsa_header));  /* Collect the interface's Link-LSAs to describe     network's optional capabilities */  type = htons (OSPF6_LSTYPE_LINK);  for (lsa = ospf6_lsdb_type_head (type, oi->lsdb); lsa;       lsa = ospf6_lsdb_type_next (type, lsa))    {      link_lsa = (struct ospf6_link_lsa *)        ((caddr_t) lsa->header + sizeof (struct ospf6_lsa_header));      network_lsa->options[0] |= link_lsa->options[0];      network_lsa->options[1] |= link_lsa->options[1];      network_lsa->options[2] |= link_lsa->options[2];    }  lsdesc = (struct ospf6_network_lsdesc *)    ((caddr_t) network_lsa + sizeof (struct ospf6_network_lsa));  /* set Link Description to the router itself */  lsdesc->router_id = oi->area->ospf6->router_id;  lsdesc++;  /* Walk through the neighbors */  for (i = listhead (oi->neighbor_list); i; nextnode (i))    {      on = (struct ospf6_neighbor *) getdata (i);      if (on->state != OSPF6_NEIGHBOR_FULL)        continue;      /* set this neighbor's Router-ID to LSA */      lsdesc->router_id = on->router_id;      lsdesc++;    }  /* Fill LSA Header */  lsa_header->age = 0;  lsa_header->type = htons (OSPF6_LSTYPE_NETWORK);  lsa_header->id = htonl (oi->interface->ifindex);  lsa_header->adv_router = oi->area->ospf6->router_id;  lsa_header->seqnum =    ospf6_new_ls_seqnum (lsa_header->type, lsa_header->id,                         lsa_header->adv_router, oi->area->lsdb);  lsa_header->length = htons ((caddr_t) lsdesc - (caddr_t) buffer);  /* LSA checksum */  ospf6_lsa_checksum (lsa_header);  /* create LSA */  lsa = ospf6_lsa_create (lsa_header);  /* Originate */  ospf6_lsa_originate_area (lsa, oi->area);  return 0;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -