#include <DatabaseDescriptionHandler.h>
Inheritance diagram for OSPF::DatabaseDescriptionHandler:

Public Member Functions | |
| DatabaseDescriptionHandler (Router *containingRouter) | |
| void | ProcessPacket (OSPFPacket *packet, Interface *intf, Neighbor *neighbor) |
Private Member Functions | |
| bool | ProcessDDPacket (OSPFDatabaseDescriptionPacket *ddPacket, Interface *intf, Neighbor *neighbor, bool inExchangeStart) |
|
|
00007 : 00008 OSPF::IMessageHandler (containingRouter) 00009 { 00010 }
|
|
||||||||||||||||||||
|
00162 {
00163 EV << " Processing packet contents (ddOptions="
00164 << ((ddPacket->getDdOptions ().I_Init) ? "I " : "_ ")
00165 << ((ddPacket->getDdOptions ().M_More) ? "M " : "_ ")
00166 << ((ddPacket->getDdOptions ().MS_MasterSlave) ? "MS" : "__")
00167 << "; seqNumber="
00168 << ddPacket->getDdSequenceNumber ()
00169 << "):\n";
00170
00171 unsigned int headerCount = ddPacket->getLsaHeadersArraySize ();
00172
00173 for (unsigned int i = 0; i < headerCount; i++) {
00174 OSPFLSAHeader& currentHeader = ddPacket->getLsaHeaders (i);
00175 LSAType lsaType = static_cast<LSAType> (currentHeader.getLsType ());
00176
00177 EV << " ";
00178 PrintLSAHeader (currentHeader);
00179
00180 if ((lsaType < RouterLSAType) || (lsaType > ASExternalLSAType) ||
00181 ((lsaType == ASExternalLSAType) && (!intf->GetArea ()->GetExternalRoutingCapability ())))
00182 {
00183 EV << " Error!\n";
00184 neighbor->ProcessEvent (OSPF::Neighbor::SequenceNumberMismatch);
00185 return false;
00186 } else {
00187 OSPF::LSAKeyType lsaKey;
00188
00189 lsaKey.linkStateID = currentHeader.getLinkStateID ();
00190 lsaKey.advertisingRouter = currentHeader.getAdvertisingRouter ().getInt ();
00191
00192 OSPFLSA* lsaInDatabase = router->FindLSA (lsaType, lsaKey, intf->GetArea ()->GetAreaID ());
00193
00194 // operator< and operator== on OSPFLSAHeaders determines which one is newer (less means older)
00195 if ((lsaInDatabase == NULL) || (lsaInDatabase->getHeader () < currentHeader)) {
00196 EV << " (newer)";
00197 neighbor->AddToRequestList (¤tHeader);
00198 }
00199 }
00200 EV << "\n";
00201 }
00202
00203 if (neighbor->GetDatabaseExchangeRelationship () == OSPF::Neighbor::Master) {
00204 neighbor->IncrementDDSequenceNumber ();
00205 if ((neighbor->GetDatabaseSummaryListCount () == 0) && !ddPacket->getDdOptions ().M_More) {
00206 neighbor->ProcessEvent (OSPF::Neighbor::ExchangeDone); // does nothing in ExchangeStart
00207 } else {
00208 if (!inExchangeStart) {
00209 neighbor->SendDatabaseDescriptionPacket ();
00210 }
00211 }
00212 } else {
00213 neighbor->SetDDSequenceNumber (ddPacket->getDdSequenceNumber ());
00214 if (!inExchangeStart) {
00215 neighbor->SendDatabaseDescriptionPacket ();
00216 }
00217 if (!ddPacket->getDdOptions ().M_More &&
00218 (neighbor->GetDatabaseSummaryListCount () == 0))
00219 {
00220 neighbor->ProcessEvent (OSPF::Neighbor::ExchangeDone); // does nothing in ExchangeStart
00221 }
00222 }
00223 return true;
00224 }
|
|
||||||||||||||||
|
00013 {
00014 router->GetMessageHandler ()->PrintEvent ("Database Description packet received", intf, neighbor);
00015
00016 OSPFDatabaseDescriptionPacket* ddPacket = check_and_cast<OSPFDatabaseDescriptionPacket*> (packet);
00017
00018 OSPF::Neighbor::NeighborStateType neighborState = neighbor->GetState ();
00019
00020 if ((ddPacket->getInterfaceMTU () <= intf->GetMTU ()) &&
00021 (neighborState > OSPF::Neighbor::AttemptState))
00022 {
00023 switch (neighborState) {
00024 case OSPF::Neighbor::TwoWayState:
00025 break;
00026 case OSPF::Neighbor::InitState:
00027 neighbor->ProcessEvent (OSPF::Neighbor::TwoWayReceived);
00028 break;
00029 case OSPF::Neighbor::ExchangeStartState:
00030 {
00031 OSPFDDOptions& ddOptions = ddPacket->getDdOptions ();
00032
00033 if (ddOptions.I_Init && ddOptions.M_More && ddOptions.MS_MasterSlave &&
00034 (ddPacket->getLsaHeadersArraySize () == 0))
00035 {
00036 if (neighbor->GetNeighborID () > router->GetRouterID ()) {
00037 OSPF::Neighbor::DDPacketID packetID;
00038 packetID.ddOptions = ddOptions;
00039 packetID.options = ddPacket->getOptions ();
00040 packetID.sequenceNumber = ddPacket->getDdSequenceNumber ();
00041
00042 neighbor->SetOptions (packetID.options);
00043 neighbor->SetDatabaseExchangeRelationship (OSPF::Neighbor::Slave);
00044 neighbor->SetDDSequenceNumber (packetID.sequenceNumber);
00045 neighbor->SetLastReceivedDDPacket (packetID);
00046
00047 if (!ProcessDDPacket (ddPacket, intf, neighbor, true)) {
00048 break;
00049 }
00050
00051 neighbor->ProcessEvent (OSPF::Neighbor::NegotiationDone);
00052 if (!neighbor->IsLinkStateRequestListEmpty () &&
00053 !neighbor->IsRequestRetransmissionTimerActive ())
00054 {
00055 neighbor->SendLinkStateRequestPacket ();
00056 neighbor->ClearRequestRetransmissionTimer ();
00057 neighbor->StartRequestRetransmissionTimer ();
00058 }
00059 } else {
00060 neighbor->SendDatabaseDescriptionPacket (true);
00061 }
00062 }
00063 if (!ddOptions.I_Init && !ddOptions.MS_MasterSlave &&
00064 (ddPacket->getDdSequenceNumber () == neighbor->GetDDSequenceNumber ()) &&
00065 (neighbor->GetNeighborID () < router->GetRouterID ()))
00066 {
00067 OSPF::Neighbor::DDPacketID packetID;
00068 packetID.ddOptions = ddOptions;
00069 packetID.options = ddPacket->getOptions ();
00070 packetID.sequenceNumber = ddPacket->getDdSequenceNumber ();
00071
00072 neighbor->SetOptions (packetID.options);
00073 neighbor->SetDatabaseExchangeRelationship (OSPF::Neighbor::Master);
00074 neighbor->SetLastReceivedDDPacket (packetID);
00075
00076 if (!ProcessDDPacket (ddPacket, intf, neighbor, true)) {
00077 break;
00078 }
00079
00080 neighbor->ProcessEvent (OSPF::Neighbor::NegotiationDone);
00081 if (!neighbor->IsLinkStateRequestListEmpty () &&
00082 !neighbor->IsRequestRetransmissionTimerActive ())
00083 {
00084 neighbor->SendLinkStateRequestPacket ();
00085 neighbor->ClearRequestRetransmissionTimer ();
00086 neighbor->StartRequestRetransmissionTimer ();
00087 }
00088 }
00089 }
00090 break;
00091 case OSPF::Neighbor::ExchangeState:
00092 {
00093 OSPF::Neighbor::DDPacketID packetID;
00094 packetID.ddOptions = ddPacket->getDdOptions ();
00095 packetID.options = ddPacket->getOptions ();
00096 packetID.sequenceNumber = ddPacket->getDdSequenceNumber ();
00097
00098 if (packetID != neighbor->GetLastReceivedDDPacket ()) {
00099 if ((packetID.ddOptions.MS_MasterSlave &&
00100 (neighbor->GetDatabaseExchangeRelationship () != OSPF::Neighbor::Slave)) ||
00101 (!packetID.ddOptions.MS_MasterSlave &&
00102 (neighbor->GetDatabaseExchangeRelationship () != OSPF::Neighbor::Master)) ||
00103 packetID.ddOptions.I_Init ||
00104 (packetID.options != neighbor->GetLastReceivedDDPacket ().options))
00105 {
00106 neighbor->ProcessEvent (OSPF::Neighbor::SequenceNumberMismatch);
00107 } else {
00108 if (((neighbor->GetDatabaseExchangeRelationship () == OSPF::Neighbor::Master) &&
00109 (packetID.sequenceNumber == neighbor->GetDDSequenceNumber ())) ||
00110 ((neighbor->GetDatabaseExchangeRelationship () == OSPF::Neighbor::Slave) &&
00111 (packetID.sequenceNumber == (neighbor->GetDDSequenceNumber () + 1))))
00112 {
00113 neighbor->SetLastReceivedDDPacket (packetID);
00114 if (!ProcessDDPacket (ddPacket, intf, neighbor, false)) {
00115 break;
00116 }
00117 if (!neighbor->IsLinkStateRequestListEmpty () &&
00118 !neighbor->IsRequestRetransmissionTimerActive ())
00119 {
00120 neighbor->SendLinkStateRequestPacket ();
00121 neighbor->ClearRequestRetransmissionTimer ();
00122 neighbor->StartRequestRetransmissionTimer ();
00123 }
00124 } else {
00125 neighbor->ProcessEvent (OSPF::Neighbor::SequenceNumberMismatch);
00126 }
00127 }
00128 } else {
00129 if (neighbor->GetDatabaseExchangeRelationship () == OSPF::Neighbor::Slave) {
00130 neighbor->RetransmitDatabaseDescriptionPacket ();
00131 }
00132 }
00133 }
00134 break;
00135 case OSPF::Neighbor::LoadingState:
00136 case OSPF::Neighbor::FullState:
00137 {
00138 OSPF::Neighbor::DDPacketID packetID;
00139 packetID.ddOptions = ddPacket->getDdOptions ();
00140 packetID.options = ddPacket->getOptions ();
00141 packetID.sequenceNumber = ddPacket->getDdSequenceNumber ();
00142
00143 if ((packetID != neighbor->GetLastReceivedDDPacket ()) ||
00144 (packetID.ddOptions.I_Init))
00145 {
00146 neighbor->ProcessEvent (OSPF::Neighbor::SequenceNumberMismatch);
00147 } else {
00148 if (neighbor->GetDatabaseExchangeRelationship () == OSPF::Neighbor::Slave) {
00149 if (!neighbor->RetransmitDatabaseDescriptionPacket ()) {
00150 neighbor->ProcessEvent (OSPF::Neighbor::SequenceNumberMismatch);
00151 }
00152 }
00153 }
00154 }
00155 break;
00156 default: break;
00157 }
00158 }
00159 }
|
1.4.1