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

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

netdev: Create netdev_queue abstraction.



A netdev_queue is an entity managed by a qdisc.

Currently there is one RX and one TX queue, and a netdev_queue merely
contains a backpointer to the net_device.

The Qdisc struct is augmented with a netdev_queue pointer as well.

Eventually the 'dev' Qdisc member will go away and we will have the
resulting hierarchy:

	net_device --> netdev_queue --> Qdisc

Also, qdisc_alloc() and qdisc_create_dflt() now take a netdev_queue
pointer argument.

Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent e65d22e1
Loading
Loading
Loading
Loading
+7 −0
Original line number Diff line number Diff line
@@ -448,6 +448,10 @@ static inline void napi_synchronize(const struct napi_struct *n)
# define napi_synchronize(n)	barrier()
#endif

struct netdev_queue {
	struct net_device	*dev;
};

/*
 *	The DEVICE structure.
 *	Actually, this whole structure is a big mistake.  It mixes I/O
@@ -624,6 +628,9 @@ struct net_device

	unsigned char		broadcast[MAX_ADDR_LEN];	/* hw bcast add	*/

	struct netdev_queue	rx_queue;
	struct netdev_queue	tx_queue;

	/* ingress path synchronizer */
	spinlock_t		ingress_lock;
	struct Qdisc		*qdisc_ingress;
+5 −1
Original line number Diff line number Diff line
@@ -37,6 +37,7 @@ struct Qdisc
	u32			parent;
	atomic_t		refcnt;
	struct sk_buff_head	q;
	struct netdev_queue	*dev_queue;
	struct net_device	*dev;
	struct list_head	list;

@@ -216,8 +217,11 @@ extern void dev_deactivate(struct net_device *dev);
extern void qdisc_reset(struct Qdisc *qdisc);
extern void qdisc_destroy(struct Qdisc *qdisc);
extern void qdisc_tree_decrease_qlen(struct Qdisc *qdisc, unsigned int n);
extern struct Qdisc *qdisc_alloc(struct net_device *dev, struct Qdisc_ops *ops);
extern struct Qdisc *qdisc_alloc(struct net_device *dev,
				 struct netdev_queue *dev_queue,
				 struct Qdisc_ops *ops);
extern struct Qdisc *qdisc_create_dflt(struct net_device *dev,
				       struct netdev_queue *dev_queue,
				       struct Qdisc_ops *ops, u32 parentid);
extern void tcf_destroy(struct tcf_proto *tp);
extern void tcf_destroy_chain(struct tcf_proto **fl);
+8 −0
Original line number Diff line number Diff line
@@ -4072,6 +4072,12 @@ static struct net_device_stats *internal_stats(struct net_device *dev)
	return &dev->stats;
}

static void netdev_init_queues(struct net_device *dev)
{
	dev->rx_queue.dev = dev;
	dev->tx_queue.dev = dev;
}

/**
 *	alloc_netdev_mq - allocate network device
 *	@sizeof_priv:	size of private data to allocate space for
@@ -4124,6 +4130,8 @@ struct net_device *alloc_netdev_mq(int sizeof_priv, const char *name,
	dev->egress_subqueue_count = queue_count;
	dev->gso_max_size = GSO_MAX_SIZE;

	netdev_init_queues(dev);

	dev->get_stats = internal_stats;
	netpoll_netdev_init(dev);
	setup(dev);
+4 −2
Original line number Diff line number Diff line
@@ -359,7 +359,8 @@ static int wme_qdiscop_init(struct Qdisc *qd, struct nlattr *opt)
	/* create child queues */
	for (i = 0; i < QD_NUM(hw); i++) {
		skb_queue_head_init(&q->requeued[i]);
		q->queues[i] = qdisc_create_dflt(qd->dev, &pfifo_qdisc_ops,
		q->queues[i] = qdisc_create_dflt(qd->dev, qd->dev_queue,
						 &pfifo_qdisc_ops,
						 qd->handle);
		if (!q->queues[i]) {
			q->queues[i] = &noop_qdisc;
@@ -575,7 +576,8 @@ void ieee80211_install_qdisc(struct net_device *dev)
{
	struct Qdisc *qdisc;

	qdisc = qdisc_create_dflt(dev, &wme_qdisc_ops, TC_H_ROOT);
	qdisc = qdisc_create_dflt(dev, &dev->tx_queue,
				  &wme_qdisc_ops, TC_H_ROOT);
	if (!qdisc) {
		printk(KERN_ERR "%s: qdisc installation failed\n", dev->name);
		return;
+7 −5
Original line number Diff line number Diff line
@@ -552,8 +552,8 @@ static int qdisc_graft(struct net_device *dev, struct Qdisc *parent,
 */

static struct Qdisc *
qdisc_create(struct net_device *dev, u32 parent, u32 handle,
	   struct nlattr **tca, int *errp)
qdisc_create(struct net_device *dev, struct netdev_queue *dev_queue,
	     u32 parent, u32 handle, struct nlattr **tca, int *errp)
{
	int err;
	struct nlattr *kind = tca[TCA_KIND];
@@ -593,7 +593,7 @@ qdisc_create(struct net_device *dev, u32 parent, u32 handle,
	if (ops == NULL)
		goto err_out;

	sch = qdisc_alloc(dev, ops);
	sch = qdisc_alloc(dev, dev_queue, ops);
	if (IS_ERR(sch)) {
		err = PTR_ERR(sch);
		goto err_out2;
@@ -892,10 +892,12 @@ create_n_graft:
	if (!(n->nlmsg_flags&NLM_F_CREATE))
		return -ENOENT;
	if (clid == TC_H_INGRESS)
		q = qdisc_create(dev, tcm->tcm_parent, tcm->tcm_parent,
		q = qdisc_create(dev, &dev->rx_queue,
				 tcm->tcm_parent, tcm->tcm_parent,
				 tca, &err);
	else
		q = qdisc_create(dev, tcm->tcm_parent, tcm->tcm_handle,
		q = qdisc_create(dev, &dev->tx_queue,
				 tcm->tcm_parent, tcm->tcm_handle,
				 tca, &err);
	if (q == NULL) {
		if (err == -EAGAIN)
Loading