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

📄 ospf6_message.c

📁 linux 路由软件 可支持RIP OSPF BGP等
💻 C
📖 第 1 页 / 共 5 页
字号:
          ! CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_IBIT) &&          ntohl (dbdesc->seqnum) == on->dbdesc_seqnum)        {          /* execute NegotiationDone */          thread_execute (master, negotiation_done, on, 0);          /* Record neighbor options */          memcpy (on->options, dbdesc->options, sizeof (on->options));        }      else        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Negotiation failed");          return;        }      /* fall through to exchange */    case OSPF6_NEIGHBOR_EXCHANGE:      if (! memcmp (dbdesc, &on->dbdesc_last, sizeof (struct ospf6_dbdesc)))        {          /* Duplicated DatabaseDescription is dropped by master */          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Duplicated dbdesc discarded by Master, ignore");          return;        }      if (CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_MSBIT))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Master/Slave bit mismatch");          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      if (CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_IBIT))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Initialize bit mismatch");          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      if (memcmp (on->options, dbdesc->options, sizeof (on->options)))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Option field mismatch");          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      if (ntohl (dbdesc->seqnum) != on->dbdesc_seqnum)        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Sequence number mismatch (%#lx expected)",                       (u_long) on->dbdesc_seqnum);          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      break;    case OSPF6_NEIGHBOR_LOADING:    case OSPF6_NEIGHBOR_FULL:      if (! memcmp (dbdesc, &on->dbdesc_last, sizeof (struct ospf6_dbdesc)))        {          /* Duplicated DatabaseDescription is dropped by master */          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Duplicated dbdesc discarded by Master, ignore");          return;        }      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Not duplicate dbdesc in state %s",                   ospf6_neighbor_state_str[on->state]);      thread_add_event (master, seqnumber_mismatch, on, 0);      return;    default:      assert (0);      break;    }  /* Process LSA headers */  for (p = (char *) ((caddr_t) dbdesc + sizeof (struct ospf6_dbdesc));       p + sizeof (struct ospf6_lsa_header) <= OSPF6_MESSAGE_END (oh);       p += sizeof (struct ospf6_lsa_header))    {      struct ospf6_lsa *his, *mine;      struct ospf6_lsdb *lsdb = NULL;      his = ospf6_lsa_create_headeronly ((struct ospf6_lsa_header *) p);      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("%s", his->name);      switch (OSPF6_LSA_SCOPE (his->header->type))        {        case OSPF6_SCOPE_LINKLOCAL:          lsdb = on->ospf6_if->lsdb;          break;        case OSPF6_SCOPE_AREA:          lsdb = on->ospf6_if->area->lsdb;          break;        case OSPF6_SCOPE_AS:          lsdb = on->ospf6_if->area->ospf6->lsdb;          break;        case OSPF6_SCOPE_RESERVED:          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Ignoring LSA of reserved scope");          ospf6_lsa_delete (his);          continue;          break;        }      if (ntohs (his->header->type) == OSPF6_LSTYPE_AS_EXTERNAL &&          IS_AREA_STUB (on->ospf6_if->area))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("SeqNumMismatch (E-bit mismatch), discard");          ospf6_lsa_delete (his);          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      mine = ospf6_lsdb_lookup (his->header->type, his->header->id,                                his->header->adv_router, lsdb);      if (mine == NULL)        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Add request (No database copy)");          ospf6_lsdb_add (his, on->request_list);        }      else if (ospf6_lsa_compare (his, mine) < 0)        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Add request (Received MoreRecent)");          ospf6_lsdb_add (his, on->request_list);        }      else        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Discard (Existing MoreRecent)");          ospf6_lsa_delete (his);        }    }  if (p != OSPF6_MESSAGE_END (oh))    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Trailing garbage ignored");    }  /* Increment sequence number */  on->dbdesc_seqnum ++;  /* schedule send lsreq */  if (on->thread_send_lsreq == NULL)    on->thread_send_lsreq =      thread_add_event (master, ospf6_lsreq_send, on, 0);  THREAD_OFF (on->thread_send_dbdesc);  /* More bit check */  if (! CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_MBIT) &&      ! CHECK_FLAG (on->dbdesc_bits, OSPF6_DBDESC_MBIT))    thread_add_event (master, exchange_done, on, 0);  else    on->thread_send_dbdesc =      thread_add_event (master, ospf6_dbdesc_send_newone, on, 0);  /* save last received dbdesc */  memcpy (&on->dbdesc_last, dbdesc, sizeof (struct ospf6_dbdesc));}static voidospf6_dbdesc_recv_slave (struct ospf6_header *oh,                         struct ospf6_neighbor *on){  struct ospf6_dbdesc *dbdesc;  char *p;  dbdesc = (struct ospf6_dbdesc *)    ((caddr_t) oh + sizeof (struct ospf6_header));  if (on->state < OSPF6_NEIGHBOR_INIT)    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Neighbor state less than Init, ignore");      return;    }  switch (on->state)    {    case OSPF6_NEIGHBOR_TWOWAY:      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Neighbor state is 2-Way, ignore");      return;    case OSPF6_NEIGHBOR_INIT:      thread_execute (master, twoway_received, on, 0);      if (on->state != OSPF6_NEIGHBOR_EXSTART)        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Neighbor state is not ExStart, ignore");          return;        }      /* else fall through to ExStart */    case OSPF6_NEIGHBOR_EXSTART:      /* If the neighbor is Master, act as Slave. Schedule negotiation_done         and process LSA Headers. Otherwise, ignore this message */      if (CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_IBIT) &&          CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_MBIT) &&          CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_MSBIT) &&          ntohs (oh->length) == sizeof (struct ospf6_header) +                                sizeof (struct ospf6_dbdesc))        {          /* set the master/slave bit to slave */          UNSET_FLAG (on->dbdesc_bits, OSPF6_DBDESC_MSBIT);          /* set the DD sequence number to one specified by master */          on->dbdesc_seqnum = ntohl (dbdesc->seqnum);          /* schedule NegotiationDone */          thread_execute (master, negotiation_done, on, 0);          /* Record neighbor options */          memcpy (on->options, dbdesc->options, sizeof (on->options));        }      else        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Negotiation failed");          return;        }      break;    case OSPF6_NEIGHBOR_EXCHANGE:      if (! memcmp (dbdesc, &on->dbdesc_last, sizeof (struct ospf6_dbdesc)))        {          /* Duplicated DatabaseDescription causes slave to retransmit */          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Duplicated dbdesc causes retransmit");          THREAD_OFF (on->thread_send_dbdesc);          on->thread_send_dbdesc =            thread_add_event (master, ospf6_dbdesc_send, on, 0);          return;        }      if (! CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_MSBIT))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Master/Slave bit mismatch");          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      if (CHECK_FLAG (dbdesc->bits, OSPF6_DBDESC_IBIT))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Initialize bit mismatch");          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      if (memcmp (on->options, dbdesc->options, sizeof (on->options)))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Option field mismatch");          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      if (ntohl (dbdesc->seqnum) != on->dbdesc_seqnum + 1)        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Sequence number mismatch (%#lx expected)",                       (u_long) on->dbdesc_seqnum + 1);          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      break;    case OSPF6_NEIGHBOR_LOADING:    case OSPF6_NEIGHBOR_FULL:      if (! memcmp (dbdesc, &on->dbdesc_last, sizeof (struct ospf6_dbdesc)))        {          /* Duplicated DatabaseDescription causes slave to retransmit */          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Duplicated dbdesc causes retransmit");          THREAD_OFF (on->thread_send_dbdesc);          on->thread_send_dbdesc =            thread_add_event (master, ospf6_dbdesc_send, on, 0);          return;        }      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Not duplicate dbdesc in state %s",                   ospf6_neighbor_state_str[on->state]);      thread_add_event (master, seqnumber_mismatch, on, 0);      return;    default:      assert (0);      break;    }  /* Process LSA headers */  for (p = (char *) ((caddr_t) dbdesc + sizeof (struct ospf6_dbdesc));       p + sizeof (struct ospf6_lsa_header) <= OSPF6_MESSAGE_END (oh);       p += sizeof (struct ospf6_lsa_header))    {      struct ospf6_lsa *his, *mine;      struct ospf6_lsdb *lsdb = NULL;      his = ospf6_lsa_create_headeronly ((struct ospf6_lsa_header *) p);      switch (OSPF6_LSA_SCOPE (his->header->type))        {        case OSPF6_SCOPE_LINKLOCAL:          lsdb = on->ospf6_if->lsdb;          break;        case OSPF6_SCOPE_AREA:          lsdb = on->ospf6_if->area->lsdb;          break;        case OSPF6_SCOPE_AS:          lsdb = on->ospf6_if->area->ospf6->lsdb;          break;        case OSPF6_SCOPE_RESERVED:          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Ignoring LSA of reserved scope");          ospf6_lsa_delete (his);          continue;          break;        }      if (OSPF6_LSA_SCOPE (his->header->type) == OSPF6_SCOPE_AS &&          IS_AREA_STUB (on->ospf6_if->area))        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("E-bit mismatch with LSA Headers");          ospf6_lsa_delete (his);          thread_add_event (master, seqnumber_mismatch, on, 0);          return;        }      mine = ospf6_lsdb_lookup (his->header->type, his->header->id,                                his->header->adv_router, lsdb);      if (mine == NULL || ospf6_lsa_compare (his, mine) < 0)        {          if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))            zlog_info ("Add request-list: %s", his->name);          ospf6_lsdb_add (his, on->request_list);        }      else        ospf6_lsa_delete (his);    }  if (p != OSPF6_MESSAGE_END (oh))    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Trailing garbage ignored");    }  /* Set sequence number to Master's */  on->dbdesc_seqnum = ntohl (dbdesc->seqnum);  /* schedule send lsreq */  if (on->thread_send_lsreq == NULL)    on->thread_send_lsreq =      thread_add_event (master, ospf6_lsreq_send, on, 0);  THREAD_OFF (on->thread_send_dbdesc);  on->thread_send_dbdesc =    thread_add_event (master, ospf6_dbdesc_send_newone, on, 0);  /* save last received dbdesc */  memcpy (&on->dbdesc_last, dbdesc, sizeof (struct ospf6_dbdesc));}voidospf6_dbdesc_recv (struct in6_addr *src, struct in6_addr *dst,                   struct ospf6_interface *oi, struct ospf6_header *oh){  struct ospf6_neighbor *on;  struct ospf6_dbdesc *dbdesc;  if (ospf6_header_examin (src, dst, oi, oh) != MSG_OK)    return;  on = ospf6_neighbor_lookup (oh->router_id, oi);  if (on == NULL)    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Neighbor not found, ignore");      return;    }  if (memcmp (src, &on->linklocal_addr, sizeof (struct in6_addr)))    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Seems to be from Secondary I/F of the neighbor, ignore");      return;    }  dbdesc = (struct ospf6_dbdesc *)    ((caddr_t) oh + sizeof (struct ospf6_header));  /* Interface MTU check */  if (ntohs (dbdesc->ifmtu) != oi->ifmtu)    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("I/F MTU mismatch");      return;    }  if (dbdesc->reserved1 || dbdesc->reserved2)    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))        zlog_info ("Non-0 reserved field in %s's DbDesc, correct",                   on->name);      dbdesc->reserved1 = 0;      dbdesc->reserved2 = 0;    }  if (ntohl (oh->router_id) < ntohl (ospf6->router_id))    ospf6_dbdesc_recv_master (oh, on);  else if (ntohl (ospf6->router_id) < ntohl (oh->router_id))    ospf6_dbdesc_recv_slave (oh, on);  else    {      if (IS_OSPF6_DEBUG_MESSAGE (oh->type, RECV))

⌨️ 快捷键说明

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