Yeah! It finally works! The default route was missing, that was the only problem!

I established a connection with PPPoE and pinged goole and osnews. Net+ loaded half of www.osnews.com but then crashed because of a bug in our DNS resolver.
There is one more bug to fix: our core stack module does not remove the routes when an interface is deleted.
Thus, there will always remain the route(s) from the last connection(s).


git-svn-id: file:///srv/svn/repos/haiku/trunk/current@5910 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Waldemar Kornewald 2004-01-05 13:34:11 +00:00
parent a243b54e73
commit 86c13dda5a
6 changed files with 104 additions and 29 deletions

View File

@ -179,10 +179,16 @@ IPCP::Down()
status_t
IPCP::Send(struct mbuf *packet, uint16 protocolNumber = IPCP_PROTOCOL)
{
#if DEBUG
printf("IPCP: Send(0x%X)\n", protocolNumber);
#endif
if((protocolNumber == IP_PROTOCOL && State() == PPP_OPENED_STATE)
|| protocolNumber == IPCP_PROTOCOL)
return SendToNext(packet, protocolNumber);
printf("IPCP: Send() failed because of wrong state or protocol number!\n");
m_freem(packet);
return B_ERROR;
}
@ -191,6 +197,10 @@ IPCP::Send(struct mbuf *packet, uint16 protocolNumber = IPCP_PROTOCOL)
status_t
IPCP::Receive(struct mbuf *packet, uint16 protocolNumber)
{
#if DEBUG
printf("IPCP: Receive(0x%X)\n", protocolNumber);
#endif
if(!packet)
return B_ERROR;
@ -359,10 +369,14 @@ IPCP::UpdateAddresses()
if(State() != PPP_OPENED_STATE && !Interface().DoesDialOnDemand())
return;
in_addr_t netmask;
struct sockaddr_in gateway;
struct in_aliasreq inreq;
struct ifreq ifreqAddress, ifreqDestination;
memset(&inreq, 0, sizeof(struct in_aliasreq));
memset(&ifreqAddress, 0, sizeof(struct ifreq));
memset(&ifreqDestination, 0, sizeof(struct ifreq));
// create local address
inreq.ifra_addr.sin_family = AF_INET;
if(fLocalRequests.address != INADDR_ANY)
inreq.ifra_addr.sin_addr.s_addr = fLocalRequests.address;
@ -370,42 +384,59 @@ IPCP::UpdateAddresses()
inreq.ifra_addr.sin_addr.s_addr = INADDR_BROADCAST;
else
inreq.ifra_addr.sin_addr.s_addr = fLocalConfiguration.address;
inreq.ifra_addr.sin_len = sizeof(sockaddr_in);
memcpy(&ifreqAddress.ifr_addr, &inreq.ifra_addr, sizeof(sockaddr_in));
inreq.ifra_addr.sin_len = sizeof(struct sockaddr_in);
memcpy(&ifreqAddress.ifr_addr, &inreq.ifra_addr, sizeof(struct sockaddr_in));
inreq.ifra_dstaddr.sin_family = AF_INET;
// create destination address
gateway.sin_family = AF_INET;
if(fPeerRequests.address != INADDR_ANY)
inreq.ifra_dstaddr.sin_addr.s_addr = fPeerRequests.address;
gateway.sin_addr.s_addr = fPeerRequests.address;
else if(fPeerConfiguration.address == INADDR_ANY)
inreq.ifra_dstaddr.sin_addr.s_addr = INADDR_BROADCAST;
gateway.sin_addr.s_addr = INADDR_BROADCAST;
else
inreq.ifra_dstaddr.sin_addr.s_addr = fPeerConfiguration.address;
inreq.ifra_dstaddr.sin_len = sizeof(sockaddr_in);
memcpy(&ifreqDestination.ifr_dstaddr, &inreq.ifra_dstaddr, sizeof(sockaddr_in));
gateway.sin_addr.s_addr = fPeerConfiguration.address;
gateway.sin_len = sizeof(struct sockaddr_in);
memcpy(&inreq.ifra_dstaddr, &gateway,
sizeof(struct sockaddr_in));
memcpy(&ifreqDestination.ifr_dstaddr, &inreq.ifra_dstaddr,
sizeof(struct sockaddr_in));
// create netmask
inreq.ifra_mask.sin_family = AF_INET;
if(fLocalRequests.netmask != INADDR_ANY)
netmask = fLocalRequests.netmask;
else if(State() != PPP_OPENED_STATE)
netmask = INADDR_BROADCAST;
else
netmask = 0x80000000;
inreq.ifra_mask.sin_addr.s_addr = netmask;
inreq.ifra_mask.sin_len = sizeof(sockaddr_in);
inreq.ifra_mask.sin_addr.s_addr = fLocalRequests.netmask;
inreq.ifra_mask.sin_len = sizeof(struct sockaddr_in);
// tell stack to use these values
if(in_control(NULL, SIOCAIFADDR, (caddr_t) &inreq,
Interface().Ifnet()) != B_OK)
printf("IPCP: UpdateAddress(): SIOCAIFADDR returned error!\n");
if(in_control(NULL, SIOCSIFADDR, (caddr_t) &ifreqAddress,
Interface().Ifnet()) != B_OK)
printf("IPCP: UpdateAddress(): SIOCSIFADDR returned error!\n");
if(in_control(NULL, SIOCSIFDSTADDR, (caddr_t) &ifreqDestination,
Interface().Ifnet()) != B_OK)
printf("IPCP: UpdateAddress(): SIOCSIFDSTADDR returned error!\n");
memcpy(&inreq.ifra_addr, &inreq.ifra_mask, sizeof(struct sockaddr_in));
// SIOCISFNETMASK wants the netmask to be in ifra_addr
if(in_control(NULL, SIOCSIFNETMASK, (caddr_t) &inreq,
Interface().Ifnet()) != B_OK)
printf("IPCP: UpdateAddress(): SIOCSIFNETMASK returned error!\n");
// the netmask is optional for PPP interfaces
if(fLocalRequests.netmask != INADDR_ANY) {
if(in_control(NULL, SIOCSIFNETMASK, (caddr_t) &inreq.ifra_mask,
Interface().Ifnet()) != B_OK)
printf("IPCP: UpdateAddress(): SIOCSIFNETMASK returned error!\n");
}
// add default/subnet route
struct rtentry *rt;
struct sockaddr_in destination;
destination.sin_family = AF_INET;
destination.sin_addr.s_addr = fLocalRequests.netmask;
if(fLocalRequests.netmask == INADDR_ANY)
destination.sin_len = 0;
else
destination.sin_len = sizeof(struct sockaddr_in);
if(rtrequest(RTM_ADD, (struct sockaddr*) &destination, (struct sockaddr*) &gateway,
(struct sockaddr*) &inreq.ifra_mask, RTF_UP | RTF_GATEWAY, &rt) != B_OK)
printf("IPCP: UpdateAddress(): could not add default route!\n");
--rt->rt_refcnt;
}

View File

@ -282,14 +282,16 @@ PPPoEDevice::CountOutputBytes() const
status_t
PPPoEDevice::Send(struct mbuf *packet, uint16 protocolNumber = 0)
{
// Send() is only for PPP packets. PPPoE packets are sent directly to ethernet.
#if DEBUG
printf("PPPoEDevice: Send()\n");
dump_packet(packet);
#endif
if(!packet)
return B_ERROR;
else if(InitCheck() != B_OK || protocolNumber != 0) {
printf("PPPoEDevice::Send(): InitCheck() != B_OK!\n");
m_freem(packet);
return B_ERROR;
}
@ -297,6 +299,7 @@ PPPoEDevice::Send(struct mbuf *packet, uint16 protocolNumber = 0)
LockerHelper locker(fLock);
if(!IsUp()) {
printf("PPPoEDevice::Send(): no connection!\n");
m_freem(packet);
return PPP_NO_CONNECTION;
}

View File

@ -648,16 +648,27 @@ PPPInterface::ProtocolAt(int32 index) const
PPPProtocol*
PPPInterface::ProtocolFor(uint16 protocolNumber, PPPProtocol *start = NULL) const
{
#if DEBUG
printf("PPPInterface: ProtocolFor(%X), p&=%X\n", protocolNumber,
protocolNumber & 0x7FFF);
#endif
PPPProtocol *current = start ? start : FirstProtocol();
for(; current; current = current->NextProtocol()) {
#if DEBUG
printf("PPPInterface: ProtocolFor(): c=%X, c&=%X\n", current->ProtocolNumber(),
current->ProtocolNumber() & 0x7FFF);
#endif
if(current->ProtocolNumber() == protocolNumber
|| (current->Flags() & PPP_INCLUDES_NCP
&& current->ProtocolNumber() & 0x7FFF == protocolNumber & 0x7FFF))
&& (current->ProtocolNumber() & 0x7FFF)
== (protocolNumber & 0x7FFF)))
return current;
}
return current;
return NULL;
}
@ -1194,9 +1205,23 @@ PPPInterface::Send(struct mbuf *packet, uint16 protocolNumber)
protocol = protocol->NextProtocol() ?
ProtocolFor(protocolNumber, protocol->NextProtocol()) : NULL;
#if DEBUG
if(!protocol)
printf("PPPInterface::Send(): no protocol found!\n");
else if(!Device()->IsUp())
printf("PPPInterface::Send(): device is not up!\n");
else if(!protocol->IsEnabled())
printf("PPPInterface::Send(): protocol not enabled!\n");
else if(!IsProtocolAllowed(*protocol))
printf("PPPInterface::Send(): protocol not allowed to send!\n");
else
printf("PPPInterface::Send(): protocol allowed\n");
#endif
// make sure that protocol is allowed to send and everything is up
if(!Device()->IsUp() || !protocol || !protocol->IsEnabled()
|| !IsProtocolAllowed(*protocol)) {
printf("PPPInterface::Send(): cannot send!\n");
m_freem(packet);
return B_ERROR;
}
@ -1272,6 +1297,10 @@ PPPInterface::Receive(struct mbuf *packet, uint16 protocolNumber)
for(; protocol;
protocol = protocol->NextProtocol() ?
ProtocolFor(protocolNumber, protocol->NextProtocol()) : NULL) {
#if DEBUG
printf("PPPInterface::Receive(): trying protocol\n");
#endif
if(!protocol->IsEnabled() || !IsProtocolAllowed(*protocol))
continue;
// skip handler if disabled or not allowed
@ -1283,6 +1312,10 @@ PPPInterface::Receive(struct mbuf *packet, uint16 protocolNumber)
return result;
}
#if DEBUG
printf("PPPInterface::Receive(): trying parent\n");
#endif
// maybe the parent interface can handle the packet
if(Parent())
return Parent()->Receive(packet, protocolNumber);

View File

@ -217,8 +217,10 @@ PPPLCP::Receive(struct mbuf *packet, uint16 protocolNumber)
if(!packet)
return B_ERROR;
if(protocolNumber != PPP_LCP_PROTOCOL)
if(protocolNumber != PPP_LCP_PROTOCOL) {
printf("PPPLCP::Receive(): wrong protocol number!\n");
return PPP_UNHANDLED;
}
ppp_lcp_packet *data = mtod(packet, ppp_lcp_packet*);

View File

@ -11,8 +11,13 @@
#include <cstring>
#include <core_funcs.h>
#ifdef _KERNEL_MODE
#include <kernel_cpp.h>
#define spawn_thread spawn_kernel_thread
#define printf dprintf
#else
#include <cstdio>
#endif
@ -56,6 +61,7 @@ PPPLayer::SendToNext(struct mbuf *packet, uint16 protocolNumber) const
else
return Next()->SendToNext(packet, protocolNumber);
} else {
printf("PPPLayer: SendToNext() failed because there is no next handler!\n");
m_freem(packet);
return B_ERROR;
}

View File

@ -20,7 +20,7 @@
#ifdef _KERNEL_MODE
#define spawn_thread spawn_kernel_thread
#define printf dprintf
#else DEBUG
#else
#include <cstdio>
#endif
@ -1893,7 +1893,7 @@ bool
PPPStateMachine::SendCodeReject(struct mbuf *packet, uint16 protocolNumber, uint8 code)
{
#if DEBUG
printf("PPPSM: SendCodeReject(protocolNumber=%d;code=%d) state=%d phase=%d\n",
printf("PPPSM: SendCodeReject(protocolNumber=%X;code=%d) state=%d phase=%d\n",
protocolNumber, code, State(), Phase());
#endif