Make ppp a cloning device. Based on the work of Quentin Garnier.
This commit is contained in:
parent
e3ceb08f8d
commit
f11e795a0f
179
sys/net/if_ppp.c
179
sys/net/if_ppp.c
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: if_ppp.c,v 1.90 2004/07/03 18:11:33 dyoung Exp $ */
|
||||
/* $NetBSD: if_ppp.c,v 1.91 2004/12/05 04:15:16 christos Exp $ */
|
||||
/* Id: if_ppp.c,v 1.6 1997/03/04 03:33:00 paulus Exp */
|
||||
|
||||
/*
|
||||
@ -102,7 +102,7 @@
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
__KERNEL_RCSID(0, "$NetBSD: if_ppp.c,v 1.90 2004/07/03 18:11:33 dyoung Exp $");
|
||||
__KERNEL_RCSID(0, "$NetBSD: if_ppp.c,v 1.91 2004/12/05 04:15:16 christos Exp $");
|
||||
|
||||
#include "ppp.h"
|
||||
|
||||
@ -202,7 +202,17 @@ void pppintr(void *);
|
||||
#define M_HIGHPRI M_LINK0 /* output packet for sc_fastq */
|
||||
#define M_ERRMARK M_LINK1 /* rx packet following lost/corrupted pkt */
|
||||
|
||||
struct ppp_softc ppp_softc[NPPP];
|
||||
static int ppp_clone_create(struct if_clone *, int);
|
||||
static int ppp_clone_destroy(struct ifnet *);
|
||||
|
||||
static struct ppp_softc *ppp_create(const char *, int);
|
||||
|
||||
static LIST_HEAD(, ppp_softc) ppp_softc_list;
|
||||
|
||||
struct if_clone ppp_cloner =
|
||||
IF_CLONE_INITIALIZER("ppp", ppp_clone_create, ppp_clone_destroy);
|
||||
|
||||
static struct simplelock ppp_list_mutex = SIMPLELOCK_INITIALIZER;
|
||||
|
||||
#ifdef PPP_COMPRESS
|
||||
/*
|
||||
@ -232,35 +242,104 @@ struct compressor *ppp_compressors[PPP_COMPRESSORS_MAX] = {
|
||||
void
|
||||
pppattach()
|
||||
{
|
||||
struct ppp_softc *sc;
|
||||
int i = 0;
|
||||
LIST_INIT(&ppp_softc_list);
|
||||
if_clone_attach(&ppp_cloner);
|
||||
}
|
||||
|
||||
for (sc = ppp_softc; i < NPPP; sc++) {
|
||||
sc->sc_unit = i; /* XXX */
|
||||
snprintf(sc->sc_if.if_xname, sizeof(sc->sc_if.if_xname), "ppp%d", i++);
|
||||
callout_init(&sc->sc_timo_ch);
|
||||
sc->sc_if.if_softc = sc;
|
||||
sc->sc_if.if_mtu = PPP_MTU;
|
||||
sc->sc_if.if_flags = IFF_POINTOPOINT | IFF_MULTICAST;
|
||||
sc->sc_if.if_type = IFT_PPP;
|
||||
sc->sc_if.if_hdrlen = PPP_HDRLEN;
|
||||
sc->sc_if.if_dlt = DLT_NULL;
|
||||
sc->sc_if.if_ioctl = pppsioctl;
|
||||
sc->sc_if.if_output = pppoutput;
|
||||
#ifdef ALTQ
|
||||
sc->sc_if.if_start = ppp_ifstart;
|
||||
#endif
|
||||
IFQ_SET_MAXLEN(&sc->sc_if.if_snd, IFQ_MAXLEN);
|
||||
sc->sc_inq.ifq_maxlen = IFQ_MAXLEN;
|
||||
sc->sc_fastq.ifq_maxlen = IFQ_MAXLEN;
|
||||
sc->sc_rawq.ifq_maxlen = IFQ_MAXLEN;
|
||||
IFQ_SET_READY(&sc->sc_if.if_snd);
|
||||
if_attach(&sc->sc_if);
|
||||
if_alloc_sadl(&sc->sc_if);
|
||||
#if NBPFILTER > 0
|
||||
bpfattach(&sc->sc_if, DLT_NULL, 0);
|
||||
static struct ppp_softc *
|
||||
ppp_create(const char *name, int unit)
|
||||
{
|
||||
struct ppp_softc *sc, *sci, *scl = NULL;
|
||||
|
||||
MALLOC(sc, struct ppp_softc *, sizeof(*sc), M_DEVBUF, M_WAIT|M_ZERO);
|
||||
|
||||
simple_lock(&ppp_list_mutex);
|
||||
if (unit == -1) {
|
||||
int i = 0;
|
||||
LIST_FOREACH(sci, &ppp_softc_list, sc_iflist) {
|
||||
scl = sci;
|
||||
if (i < sci->sc_unit) {
|
||||
unit = i;
|
||||
break;
|
||||
} else {
|
||||
#ifdef DIAGNOSTIC
|
||||
KASSERT(i == sci->sc_unit);
|
||||
#endif
|
||||
i++;
|
||||
}
|
||||
}
|
||||
if (unit == -1)
|
||||
unit = i;
|
||||
} else {
|
||||
LIST_FOREACH(sci, &ppp_softc_list, sc_iflist) {
|
||||
scl = sci;
|
||||
if (unit < sci->sc_unit)
|
||||
break;
|
||||
else if (unit == sci->sc_unit) {
|
||||
FREE(sc, M_DEVBUF);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (sci != NULL)
|
||||
LIST_INSERT_BEFORE(sci, sc, sc_iflist);
|
||||
else if (scl != NULL)
|
||||
LIST_INSERT_AFTER(scl, sc, sc_iflist);
|
||||
else
|
||||
LIST_INSERT_HEAD(&ppp_softc_list, sc, sc_iflist);
|
||||
|
||||
simple_unlock(&ppp_list_mutex);
|
||||
|
||||
(void)snprintf(sc->sc_if.if_xname, sizeof(sc->sc_if.if_xname), "%s%d",
|
||||
name, sc->sc_unit = unit);
|
||||
callout_init(&sc->sc_timo_ch);
|
||||
sc->sc_if.if_softc = sc;
|
||||
sc->sc_if.if_mtu = PPP_MTU;
|
||||
sc->sc_if.if_flags = IFF_POINTOPOINT | IFF_MULTICAST;
|
||||
sc->sc_if.if_type = IFT_PPP;
|
||||
sc->sc_if.if_hdrlen = PPP_HDRLEN;
|
||||
sc->sc_if.if_dlt = DLT_NULL;
|
||||
sc->sc_if.if_ioctl = pppsioctl;
|
||||
sc->sc_if.if_output = pppoutput;
|
||||
#ifdef ALTQ
|
||||
sc->sc_if.if_start = ppp_ifstart;
|
||||
#endif
|
||||
IFQ_SET_MAXLEN(&sc->sc_if.if_snd, IFQ_MAXLEN);
|
||||
sc->sc_inq.ifq_maxlen = IFQ_MAXLEN;
|
||||
sc->sc_fastq.ifq_maxlen = IFQ_MAXLEN;
|
||||
sc->sc_rawq.ifq_maxlen = IFQ_MAXLEN;
|
||||
IFQ_SET_READY(&sc->sc_if.if_snd);
|
||||
if_attach(&sc->sc_if);
|
||||
if_alloc_sadl(&sc->sc_if);
|
||||
#if NBPFILTER > 0
|
||||
bpfattach(&sc->sc_if, DLT_NULL, 0);
|
||||
#endif
|
||||
return sc;
|
||||
}
|
||||
|
||||
static int
|
||||
ppp_clone_create(struct if_clone *ifc, int unit)
|
||||
{
|
||||
return ppp_create(ifc->ifc_name, unit) == NULL ? EEXIST : 0;
|
||||
}
|
||||
|
||||
static int
|
||||
ppp_clone_destroy(struct ifnet *ifp)
|
||||
{
|
||||
struct ppp_softc *sc = (struct ppp_softc *)ifp->if_softc;
|
||||
|
||||
if (sc->sc_devp != NULL)
|
||||
return EBUSY; /* Not removing it */
|
||||
|
||||
simple_lock(&ppp_list_mutex);
|
||||
LIST_REMOVE(sc, sc_iflist);
|
||||
simple_unlock(&ppp_list_mutex);
|
||||
|
||||
if_detach(ifp);
|
||||
|
||||
FREE(sc, M_DEVBUF);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -270,32 +349,36 @@ struct ppp_softc *
|
||||
pppalloc(pid)
|
||||
pid_t pid;
|
||||
{
|
||||
int nppp, i;
|
||||
struct ppp_softc *sc;
|
||||
struct ppp_softc *sc = NULL, *scf;
|
||||
int i;
|
||||
|
||||
for (nppp = 0, sc = ppp_softc; nppp < NPPP; nppp++, sc++)
|
||||
if (sc->sc_xfer == pid) {
|
||||
sc->sc_xfer = 0;
|
||||
return sc;
|
||||
simple_lock(&ppp_list_mutex);
|
||||
for (scf = LIST_FIRST(&ppp_softc_list); scf != NULL;
|
||||
scf = LIST_NEXT(scf, sc_iflist)) {
|
||||
if (scf->sc_xfer == pid) {
|
||||
scf->sc_xfer = 0;
|
||||
simple_unlock(&ppp_list_mutex);
|
||||
return scf;
|
||||
}
|
||||
for (nppp = 0, sc = ppp_softc; nppp < NPPP; nppp++, sc++)
|
||||
if (sc->sc_devp == NULL)
|
||||
break;
|
||||
if (nppp >= NPPP)
|
||||
return NULL;
|
||||
if (scf->sc_devp == NULL && sc == NULL)
|
||||
sc = scf;
|
||||
}
|
||||
simple_lock(&ppp_list_mutex);
|
||||
|
||||
if (sc == NULL)
|
||||
sc = ppp_create(ppp_cloner.ifc_name, -1);
|
||||
|
||||
#ifdef __HAVE_GENERIC_SOFT_INTERRUPTS
|
||||
sc->sc_si = softintr_establish(IPL_SOFTNET, pppintr, sc);
|
||||
if (sc->sc_si == NULL) {
|
||||
printf("ppp%d: unable to establish softintr\n", sc->sc_unit);
|
||||
printf("%s: unable to establish softintr\n", sc->sc_if.if_xname);
|
||||
return (NULL);
|
||||
}
|
||||
#endif
|
||||
|
||||
sc->sc_flags = 0;
|
||||
sc->sc_mru = PPP_MRU;
|
||||
sc->sc_relinq = NULL;
|
||||
memset((char *)&sc->sc_stats, 0, sizeof(sc->sc_stats));
|
||||
(void)memset(&sc->sc_stats, 0, sizeof(sc->sc_stats));
|
||||
#ifdef VJC
|
||||
MALLOC(sc->sc_comp, struct slcompress *, sizeof(struct slcompress),
|
||||
M_DEVBUF, M_NOWAIT);
|
||||
@ -390,6 +473,7 @@ pppdealloc(sc)
|
||||
sc->sc_comp = 0;
|
||||
}
|
||||
#endif
|
||||
(void)ppp_clone_destroy(&sc->sc_if);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -410,7 +494,6 @@ pppioctl(sc, cmd, data, flag, p)
|
||||
struct npioctl *npi;
|
||||
time_t t;
|
||||
#ifdef PPP_FILTER
|
||||
/*###413 [cc] warning: `bp' might be used uninitialized in this function%%%*/
|
||||
struct bpf_program *bp, *nbp;
|
||||
struct bpf_insn *newcode, *oldcode;
|
||||
int newcodelen;
|
||||
@ -425,7 +508,7 @@ pppioctl(sc, cmd, data, flag, p)
|
||||
break;
|
||||
|
||||
case PPPIOCGUNIT:
|
||||
*(int *)data = sc->sc_unit; /* XXX */
|
||||
*(int *)data = sc->sc_unit;
|
||||
break;
|
||||
|
||||
case PPPIOCGFLAGS:
|
||||
@ -1202,12 +1285,10 @@ void
|
||||
pppnetisr(void)
|
||||
{
|
||||
struct ppp_softc *sc;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < NPPP; i++) {
|
||||
sc = &ppp_softc[i];
|
||||
for (sc = LIST_FIRST(&ppp_softc_list); scf != NULL;
|
||||
sc = LIST_NEXT(sc, sc_iflist))
|
||||
pppintr(sc);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: if_pppvar.h,v 1.18 2003/09/01 16:51:27 christos Exp $ */
|
||||
/* $NetBSD: if_pppvar.h,v 1.19 2004/12/05 04:15:16 christos Exp $ */
|
||||
/* Id: if_pppvar.h,v 1.3 1996/07/01 01:04:37 paulus Exp */
|
||||
|
||||
/*
|
||||
@ -143,10 +143,10 @@ struct ppp_softc {
|
||||
u_int16_t sc_outfcs; /* FCS so far for output packet */
|
||||
u_char sc_rawin_start; /* current char start */
|
||||
struct ppp_rawin sc_rawin; /* chars as received */
|
||||
LIST_ENTRY(ppp_softc) sc_iflist;
|
||||
};
|
||||
|
||||
#ifdef _KERNEL
|
||||
extern struct ppp_softc ppp_softc[];
|
||||
|
||||
struct ppp_softc *pppalloc __P((pid_t));
|
||||
void pppdealloc __P((struct ppp_softc *));
|
||||
|
Loading…
Reference in New Issue
Block a user