Fixes from brian. With some changes from me.
Allows FreeBSD to run as a PPPOE server One patch still not included.
This commit is contained in:
parent
34ed7085e3
commit
ff227a07ea
sys/netgraph
@ -98,12 +98,12 @@ NETGRAPH_INIT(pppoe, &typestruct);
|
||||
*/
|
||||
enum state {
|
||||
PPPOE_SNONE=0, /* [both] Initial state */
|
||||
PPPOE_LISTENING, /* [Daemon] Listening for discover initiation pkt */
|
||||
PPPOE_SINIT, /* [Client] Sent discovery initiation */
|
||||
PPPOE_PRIMED, /* [Server] Received discovery initiation */
|
||||
PPPOE_SOFFER, /* [Server] Sent offer message */
|
||||
PPPOE_PRIMED, /* [Server] Awaiting PADI from daemon */
|
||||
PPPOE_SOFFER, /* [Server] Sent offer message (got PADI)*/
|
||||
PPPOE_SREQ, /* [Client] Sent a Request */
|
||||
PPPOE_LISTENING, /* [Server] Listening for discover initiation msg */
|
||||
PPPOE_NEWCONNECTED, /* [Both] Connection established, No data received */
|
||||
PPPOE_NEWCONNECTED, /* [Server] Connection established, No data received */
|
||||
PPPOE_CONNECTED, /* [Both] Connection established, Data received */
|
||||
PPPOE_DEAD /* [Both] */
|
||||
};
|
||||
@ -833,7 +833,7 @@ AAA
|
||||
*/
|
||||
printf("packet fragmented\n");
|
||||
LEAVE(EMSGSIZE);
|
||||
}
|
||||
}
|
||||
|
||||
switch(code) {
|
||||
case PADI_CODE:
|
||||
@ -975,8 +975,8 @@ AAA
|
||||
insert_tag(sp, utag); /* ac_cookie */
|
||||
scan_tags(sp, ph);
|
||||
make_packet(sp);
|
||||
sendpacket(sp);
|
||||
sp->state = PPPOE_NEWCONNECTED;
|
||||
sendpacket(sp);
|
||||
/*
|
||||
* Having sent the last Negotiation header,
|
||||
* Set up the stored packet header to
|
||||
@ -1245,7 +1245,7 @@ ng_pppoe_connect(hook_p hook)
|
||||
/*
|
||||
* Hook disconnection
|
||||
*
|
||||
* Clean up all dangling links and infirmation about the session/hook.
|
||||
* Clean up all dangling links and information about the session/hook.
|
||||
* For this type, removal of the last link destroys the node
|
||||
*/
|
||||
static int
|
||||
@ -1284,18 +1284,28 @@ AAA
|
||||
|
||||
/* generate a packet of that type */
|
||||
MGETHDR(m, M_DONTWAIT, MT_DATA);
|
||||
m->m_pkthdr.rcvif = NULL;
|
||||
m->m_pkthdr.len = m->m_len = sizeof(*wh);
|
||||
bcopy((caddr_t)wh, mtod(m, caddr_t), sizeof(*wh));
|
||||
/* Add a General error message and adjust sizes */
|
||||
wh = mtod(m, struct pppoe_full_hdr *);
|
||||
tag = wh->ph.tag;
|
||||
tag->tag_type = PTT_GEN_ERR;
|
||||
tag->tag_len = htons((u_int16_t)msglen);
|
||||
strncpy(tag->tag_data, SIGNOFF, msglen);
|
||||
m->m_pkthdr.len = (m->m_len += sizeof(*tag) + msglen);
|
||||
wh->ph.length = htons(sizeof(*tag) + msglen);
|
||||
NG_SEND_DATA(error, privp->ethernet_hook, m, dummy);
|
||||
if(m == NULL)
|
||||
printf("pppoe: Session out of mbufs\n");
|
||||
else {
|
||||
m->m_pkthdr.rcvif = NULL;
|
||||
m->m_pkthdr.len = m->m_len = sizeof(*wh);
|
||||
bcopy((caddr_t)wh, mtod(m, caddr_t),
|
||||
sizeof(*wh));
|
||||
/*
|
||||
* Add a General error message and adjust
|
||||
* sizes
|
||||
*/
|
||||
wh = mtod(m, struct pppoe_full_hdr *);
|
||||
tag = wh->ph.tag;
|
||||
tag->tag_type = PTT_GEN_ERR;
|
||||
tag->tag_len = htons((u_int16_t)msglen);
|
||||
strncpy(tag->tag_data, SIGNOFF, msglen);
|
||||
m->m_pkthdr.len = (m->m_len += sizeof(*tag) +
|
||||
msglen);
|
||||
wh->ph.length = htons(sizeof(*tag) + msglen);
|
||||
NG_SEND_DATA(error, privp->ethernet_hook, m,
|
||||
dummy);
|
||||
}
|
||||
}
|
||||
if (sp->neg) {
|
||||
untimeout(pppoe_ticker, hook, sp->neg->timeout_handle);
|
||||
@ -1384,11 +1394,16 @@ AAA
|
||||
case PPPOE_LISTENING:
|
||||
case PPPOE_DEAD:
|
||||
case PPPOE_SNONE:
|
||||
case PPPOE_NEWCONNECTED:
|
||||
case PPPOE_CONNECTED:
|
||||
printf("pppoe: sendpacket: unexpected state\n");
|
||||
break;
|
||||
|
||||
case PPPOE_NEWCONNECTED:
|
||||
/* send the PADS without a timeout - we're now connected */
|
||||
m0 = m_copypacket(sp->neg->m, M_DONTWAIT);
|
||||
NG_SEND_DATA( error, privp->ethernet_hook, m0, dummy);
|
||||
break;
|
||||
|
||||
case PPPOE_PRIMED:
|
||||
/* No packet to send, but set up the timeout */
|
||||
neg->timeout_handle = timeout(pppoe_ticker,
|
||||
|
@ -306,10 +306,10 @@ ngd_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr,
|
||||
{
|
||||
struct ngpcb *const pcbp = sotongpcb(so);
|
||||
struct sockaddr_ng *const sap = (struct sockaddr_ng *) addr;
|
||||
char *hookname = NULL;
|
||||
meta_p mp = NULL;
|
||||
int len, error;
|
||||
hook_p hook;
|
||||
hook_p hook = NULL;
|
||||
char hookname[NG_HOOKLEN + 1];
|
||||
|
||||
if ((pcbp == NULL) || (control != NULL)) {
|
||||
error = EINVAL;
|
||||
@ -319,26 +319,42 @@ ngd_send(struct socket *so, int flags, struct mbuf *m, struct sockaddr *addr,
|
||||
error = ENOTCONN;
|
||||
goto release;
|
||||
}
|
||||
if (addr == NULL) {
|
||||
error = EDESTADDRREQ;
|
||||
goto release;
|
||||
}
|
||||
/*
|
||||
* If the user used any of these ways to not specify an address
|
||||
* then handle specially.
|
||||
*/
|
||||
if ((sap == NULL)
|
||||
|| ((len = sap->sg_len) <= 2)
|
||||
|| (*sap->sg_data == '\0')) {
|
||||
if (pcbp->sockdata->node->numhooks != 1) {
|
||||
error = EDESTADDRREQ;
|
||||
goto release;
|
||||
}
|
||||
/*
|
||||
* if exactly one hook exists, just use it.
|
||||
* Special case to allow write(2) to work on an ng_socket.
|
||||
*/
|
||||
hook = LIST_FIRST(&pcbp->sockdata->node->hooks);
|
||||
} else {
|
||||
if (len > NG_HOOKLEN) {
|
||||
error = EINVAL;
|
||||
goto release;
|
||||
}
|
||||
|
||||
/* Allocate an expendable buffer for the hook name, chop off
|
||||
* the sockaddr header, and make sure it's NUL terminated */
|
||||
len = sap->sg_len - 2;
|
||||
MALLOC(hookname, char *, len + 1, M_NETGRAPH, M_WAITOK);
|
||||
if (hookname == NULL) {
|
||||
error = ENOMEM;
|
||||
goto release;
|
||||
}
|
||||
bcopy(sap->sg_data, hookname, len);
|
||||
hookname[len] = '\0';
|
||||
/*
|
||||
* chop off the sockaddr header, and make sure it's NUL
|
||||
* terminated
|
||||
*/
|
||||
bcopy(sap->sg_data, hookname, len);
|
||||
hookname[len] = '\0';
|
||||
|
||||
/* Find the correct hook from 'hookname' */
|
||||
LIST_FOREACH(hook, &pcbp->sockdata->node->hooks, hooks) {
|
||||
if (strcmp(hookname, hook->name) == 0)
|
||||
break;
|
||||
/* Find the correct hook from 'hookname' */
|
||||
LIST_FOREACH(hook, &pcbp->sockdata->node->hooks, hooks) {
|
||||
if (strcmp(hookname, hook->name) == 0)
|
||||
break;
|
||||
}
|
||||
if (hook == NULL)
|
||||
error = EHOSTUNREACH;
|
||||
}
|
||||
|
||||
/* Send data (OK if hook is NULL) */
|
||||
@ -817,7 +833,7 @@ ngs_rcvdata(hook_p hook, struct mbuf *m, meta_p meta)
|
||||
}
|
||||
|
||||
/*
|
||||
* Dook disconnection
|
||||
* Hook disconnection
|
||||
*
|
||||
* For this type, removal of the last link destroys the node
|
||||
* if the NOLINGER flag is set.
|
||||
|
@ -53,7 +53,7 @@
|
||||
|
||||
/* Commands */
|
||||
enum {
|
||||
NGM_SOCK_CMD_NOLINGER = 1, /* close the soket on with last hook */
|
||||
NGM_SOCK_CMD_NOLINGER = 1, /* close the socket with last hook */
|
||||
NGM_SOCK_CMD_LINGER /* Keep socket even if 0 hooks */
|
||||
};
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user