Pass up datagrams that are routed to this device but have no further route. (#617)

This commit is contained in:
Jonathan Hui
2016-09-16 17:27:52 -07:00
committed by GitHub
parent 18e7515b70
commit 0071edcf7a
3 changed files with 43 additions and 12 deletions
+29 -9
View File
@@ -347,18 +347,19 @@ exit:
return error;
}
void Ip6::ProcessReceiveCallback(const Message &aMessage, const MessageInfo &messageInfo, uint8_t aIpProto)
ThreadError Ip6::ProcessReceiveCallback(const Message &aMessage, const MessageInfo &messageInfo, uint8_t aIpProto)
{
ThreadError error = kThreadError_None;
Message *messageCopy = NULL;
VerifyOrExit(mReceiveIp6DatagramCallback != NULL, ;);
VerifyOrExit(mReceiveIp6DatagramCallback != NULL, error = kThreadError_NoRoute);
if (mIsReceiveIp6FilterEnabled)
{
// do not pass messages sent to/from an RLOC
VerifyOrExit(!messageInfo.GetSockAddr().IsRoutingLocator() &&
!messageInfo.GetPeerAddr().IsRoutingLocator(), ;);
!messageInfo.GetPeerAddr().IsRoutingLocator(),
error = kThreadError_NoRoute);
switch (aIpProto)
{
@@ -369,7 +370,7 @@ void Ip6::ProcessReceiveCallback(const Message &aMessage, const MessageInfo &mes
aMessage.Read(aMessage.GetOffset(), sizeof(icmp), &icmp);
// do not pass ICMP Echo Request messages
VerifyOrExit(icmp.GetType() != IcmpHeader::kTypeEchoRequest, ;);
VerifyOrExit(icmp.GetType() != IcmpHeader::kTypeEchoRequest, error = kThreadError_NoRoute);
}
break;
@@ -381,7 +382,7 @@ void Ip6::ProcessReceiveCallback(const Message &aMessage, const MessageInfo &mes
aMessage.Read(aMessage.GetOffset(), sizeof(udp), &udp);
// do not pass MLE messages
VerifyOrExit(udp.GetDestinationPort() != Mle::kUdpPort, ;);
VerifyOrExit(udp.GetDestinationPort() != Mle::kUdpPort, error = kThreadError_NoRoute);
}
break;
@@ -405,6 +406,8 @@ exit:
{
messageCopy->Free();
}
return error;
}
ThreadError Ip6::HandleDatagram(Message &message, Netif *netif, int8_t interfaceId, const void *linkMessageInfo,
@@ -515,7 +518,7 @@ ThreadError Ip6::HandleDatagram(Message &message, Netif *netif, int8_t interface
{
hopLimit = header.GetHopLimit();
message.Write(Header::GetHopLimitOffset(), Header::GetHopLimitSize(), &hopLimit);
SuccessOrExit(error = ForwardMessage(message, messageInfo));
SuccessOrExit(error = ForwardMessage(message, messageInfo, nextHeader));
}
}
@@ -529,7 +532,7 @@ exit:
return error;
}
ThreadError Ip6::ForwardMessage(Message &message, MessageInfo &messageInfo)
ThreadError Ip6::ForwardMessage(Message &message, MessageInfo &messageInfo, uint8_t ipproto)
{
ThreadError error = kThreadError_None;
int8_t interfaceId;
@@ -557,8 +560,25 @@ ThreadError Ip6::ForwardMessage(Message &message, MessageInfo &messageInfo)
}
else
{
otDumpDebgIp6("no route", &messageInfo.GetSockAddr(), 16);
ExitNow(error = kThreadError_NoRoute);
// try passing to host
error = ProcessReceiveCallback(message, messageInfo, ipproto);
switch (error)
{
case kThreadError_None:
// the caller transfers custody in the success case, so free the message here
message.Free();
break;
case kThreadError_NoRoute:
otDumpDebgIp6("no route", &messageInfo.GetSockAddr(), 16);
break;
default:
break;
}
ExitNow();
}
// submit message to interface