Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4951704b authored by David S. Miller's avatar David S. Miller
Browse files

syncppp: Fix crashes.



The syncppp layer wants a mid-level netdev private pointer.

It was using netdev->priv but that only worked by accident,
and thus this scheme was broken when the device private
allocation strategy changed.

Add a proper mid-layer private pointer for uses like this,
update syncppp and all users, and remove the HDLC_PPP broken
tag from drivers/net/wan/Kconfig

Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent c4492586
Loading
Loading
Loading
Loading
+1 −3
Original line number Diff line number Diff line
@@ -150,11 +150,9 @@ config HDLC_FR

config HDLC_PPP
	tristate "Synchronous Point-to-Point Protocol (PPP) support"
	depends on HDLC && BROKEN
	depends on HDLC
	help
	  Generic HDLC driver supporting PPP over WAN connections.
	  This module is currently broken and will cause a kernel panic
	  when a device configured in PPP mode is activated.

	  It will be replaced by new PPP implementation in Linux 2.6.26.

+7 −7
Original line number Diff line number Diff line
@@ -629,7 +629,7 @@ static void sppp_channel_init(struct channel_data *chan)
	d->base_addr = chan->cosa->datareg;
	d->irq = chan->cosa->irq;
	d->dma = chan->cosa->dma;
	d->priv = chan;
	d->ml_priv = chan;
	sppp_attach(&chan->pppdev);
	if (register_netdev(d)) {
		printk(KERN_WARNING "%s: register_netdev failed.\n", d->name);
@@ -650,7 +650,7 @@ static void sppp_channel_delete(struct channel_data *chan)

static int cosa_sppp_open(struct net_device *d)
{
	struct channel_data *chan = d->priv;
	struct channel_data *chan = d->ml_priv;
	int err;
	unsigned long flags;

@@ -690,7 +690,7 @@ static int cosa_sppp_open(struct net_device *d)

static int cosa_sppp_tx(struct sk_buff *skb, struct net_device *dev)
{
	struct channel_data *chan = dev->priv;
	struct channel_data *chan = dev->ml_priv;

	netif_stop_queue(dev);

@@ -701,7 +701,7 @@ static int cosa_sppp_tx(struct sk_buff *skb, struct net_device *dev)

static void cosa_sppp_timeout(struct net_device *dev)
{
	struct channel_data *chan = dev->priv;
	struct channel_data *chan = dev->ml_priv;

	if (test_bit(RXBIT, &chan->cosa->rxtx)) {
		chan->stats.rx_errors++;
@@ -720,7 +720,7 @@ static void cosa_sppp_timeout(struct net_device *dev)

static int cosa_sppp_close(struct net_device *d)
{
	struct channel_data *chan = d->priv;
	struct channel_data *chan = d->ml_priv;
	unsigned long flags;

	netif_stop_queue(d);
@@ -800,7 +800,7 @@ static int sppp_tx_done(struct channel_data *chan, int size)

static struct net_device_stats *cosa_net_stats(struct net_device *dev)
{
	struct channel_data *chan = dev->priv;
	struct channel_data *chan = dev->ml_priv;
	return &chan->stats;
}

@@ -1217,7 +1217,7 @@ static int cosa_sppp_ioctl(struct net_device *dev, struct ifreq *ifr,
	int cmd)
{
	int rv;
	struct channel_data *chan = dev->priv;
	struct channel_data *chan = dev->ml_priv;
	rv = cosa_ioctl_common(chan->cosa, chan, cmd, (unsigned long)ifr->ifr_data);
	if (rv == -ENOIOCTLCMD) {
		return sppp_do_ioctl(dev, ifr, cmd);
+1 −1
Original line number Diff line number Diff line
@@ -45,7 +45,7 @@ static int ppp_open(struct net_device *dev)
	int (*old_ioctl)(struct net_device *, struct ifreq *, int);
	int result;

	dev->priv = &state(hdlc)->syncppp_ptr;
	dev->ml_priv = &state(hdlc)->syncppp_ptr;
	state(hdlc)->syncppp_ptr = &state(hdlc)->pppdev;
	state(hdlc)->pppdev.dev = dev;

+6 −6
Original line number Diff line number Diff line
@@ -75,7 +75,7 @@ static void hostess_input(struct z8530_channel *c, struct sk_buff *skb)
 
static int hostess_open(struct net_device *d)
{
	struct sv11_device *sv11=d->priv;
	struct sv11_device *sv11=d->ml_priv;
	int err = -1;
	
	/*
@@ -128,7 +128,7 @@ static int hostess_open(struct net_device *d)

static int hostess_close(struct net_device *d)
{
	struct sv11_device *sv11=d->priv;
	struct sv11_device *sv11=d->ml_priv;
	/*
	 *	Discard new frames
	 */
@@ -159,14 +159,14 @@ static int hostess_close(struct net_device *d)

static int hostess_ioctl(struct net_device *d, struct ifreq *ifr, int cmd)
{
	/* struct sv11_device *sv11=d->priv;
	/* struct sv11_device *sv11=d->ml_priv;
	   z8530_ioctl(d,&sv11->sync.chanA,ifr,cmd) */
	return sppp_do_ioctl(d, ifr,cmd);
}

static struct net_device_stats *hostess_get_stats(struct net_device *d)
{
	struct sv11_device *sv11=d->priv;
	struct sv11_device *sv11=d->ml_priv;
	if(sv11)
		return z8530_get_stats(&sv11->sync.chanA);
	else
@@ -179,7 +179,7 @@ static struct net_device_stats *hostess_get_stats(struct net_device *d)
 
static int hostess_queue_xmit(struct sk_buff *skb, struct net_device *d)
{
	struct sv11_device *sv11=d->priv;
	struct sv11_device *sv11=d->ml_priv;
	return z8530_queue_xmit(&sv11->sync.chanA, skb);
}

@@ -325,6 +325,7 @@ static struct sv11_device *sv11_init(int iobase, int irq)
		/* 
		 *	Initialise the PPP components
		 */
		d->ml_priv = sv;
		sppp_attach(&sv->netdev);
		
		/*
@@ -333,7 +334,6 @@ static struct sv11_device *sv11_init(int iobase, int irq)
		
		d->base_addr = iobase;
		d->irq = irq;
		d->priv = sv;
		
		if(register_netdev(d))
		{
+1 −0
Original line number Diff line number Diff line
@@ -891,6 +891,7 @@ static int __devinit lmc_init_one(struct pci_dev *pdev,

    /* Initialize the sppp layer */
    /* An ioctl can cause a subsequent detach for raw frame interface */
    dev->ml_priv = sc;
    sc->if_type = LMC_PPP;
    sc->check = 0xBEAFCAFE;
    dev->base_addr = pci_resource_start(pdev, 0);
Loading