Merge with 2.3.99-pre1.
[linux-2.6/linux-mips.git] / drivers / net / eql.c
blobe9f0254a7c1a750f0e352e543b0bca46166e5f4f
1 /*
2 * Equalizer Load-balancer for serial network interfaces.
4 * (c) Copyright 1995 Simon "Guru Aleph-Null" Janes
5 * NCM: Network and Communications Management, Inc.
8 * This software may be used and distributed according to the terms
9 * of the GNU Public License, incorporated herein by reference.
11 * The author may be reached as simon@ncm.com, or C/O
12 * NCM
13 * Attn: Simon Janes
14 * 6803 Whittier Ave
15 * McLean VA 22101
16 * Phone: 1-703-847-0040 ext 103
19 static const char *version =
20 "Equalizer1996: $Revision: 1.2.1 $ $Date: 1996/09/22 13:52:00 $ Simon Janes (simon@ncm.com)\n";
23 * Sources:
24 * skeleton.c by Donald Becker.
25 * Inspirations:
26 * The Harried and Overworked Alan Cox
27 * Conspiracies:
28 * The Alan Cox and Mike McLagan plot to get someone else to do the code,
29 * which turned out to be me.
33 * $Log: eql.c,v $
34 * Revision 1.2 1996/04/11 17:51:52 guru
35 * Added one-line eql_remove_slave patch.
37 * Revision 1.1 1996/04/11 17:44:17 guru
38 * Initial revision
40 * Revision 3.13 1996/01/21 15:17:18 alan
41 * tx_queue_len changes.
42 * reformatted.
44 * Revision 3.12 1995/03/22 21:07:51 anarchy
45 * Added capable() checks on configuration.
46 * Moved header file.
48 * Revision 3.11 1995/01/19 23:14:31 guru
49 * slave_load = (ULONG_MAX - (ULONG_MAX / 2)) -
50 * (priority_Bps) + bytes_queued * 8;
52 * Revision 3.10 1995/01/19 23:07:53 guru
53 * back to
54 * slave_load = (ULONG_MAX - (ULONG_MAX / 2)) -
55 * (priority_Bps) + bytes_queued;
57 * Revision 3.9 1995/01/19 22:38:20 guru
58 * slave_load = (ULONG_MAX - (ULONG_MAX / 2)) -
59 * (priority_Bps) + bytes_queued * 4;
61 * Revision 3.8 1995/01/19 22:30:55 guru
62 * slave_load = (ULONG_MAX - (ULONG_MAX / 2)) -
63 * (priority_Bps) + bytes_queued * 2;
65 * Revision 3.7 1995/01/19 21:52:35 guru
66 * printk's trimmed out.
68 * Revision 3.6 1995/01/19 21:49:56 guru
69 * This is working pretty well. I gained 1 K/s in speed.. now it's just
70 * robustness and printk's to be diked out.
72 * Revision 3.5 1995/01/18 22:29:59 guru
73 * still crashes the kernel when the lock_wait thing is woken up.
75 * Revision 3.4 1995/01/18 21:59:47 guru
76 * Broken set-bit locking snapshot
78 * Revision 3.3 1995/01/17 22:09:18 guru
79 * infinite sleep in a lock somewhere..
81 * Revision 3.2 1995/01/15 16:46:06 guru
82 * Log trimmed of non-pertinent 1.x branch messages
84 * Revision 3.1 1995/01/15 14:41:45 guru
85 * New Scheduler and timer stuff...
87 * Revision 1.15 1995/01/15 14:29:02 guru
88 * Will make 1.14 (now 1.15) the 3.0 branch, and the 1.12 the 2.0 branch, the one
89 * with the dumber scheduler
91 * Revision 1.14 1995/01/15 02:37:08 guru
92 * shock.. the kept-new-versions could have zonked working
93 * stuff.. shudder
95 * Revision 1.13 1995/01/15 02:36:31 guru
96 * big changes
98 * scheduler was torn out and replaced with something smarter
100 * global names not prefixed with eql_ were renamed to protect
101 * against namespace collisions
103 * a few more abstract interfaces were added to facilitate any
104 * potential change of datastructure. the driver is still using
105 * a linked list of slaves. going to a heap would be a bit of
106 * an overkill.
108 * this compiles fine with no warnings.
110 * the locking mechanism and timer stuff must be written however,
111 * this version will not work otherwise
115 #include <linux/module.h>
117 #include <linux/kernel.h>
118 #include <linux/sched.h>
119 #include <linux/types.h>
120 #include <linux/fcntl.h>
121 #include <linux/interrupt.h>
122 #include <linux/ptrace.h>
123 #include <linux/ioport.h>
124 #include <linux/in.h>
125 #include <linux/malloc.h>
126 #include <linux/string.h>
127 #include <asm/system.h>
128 #include <asm/bitops.h>
129 #include <asm/io.h>
130 #include <asm/dma.h>
131 #include <asm/uaccess.h>
132 #include <linux/errno.h>
133 #include <linux/init.h>
135 #include <linux/netdevice.h>
136 #include <linux/if.h>
137 #include <linux/if_arp.h>
138 #include <linux/timer.h>
140 #include <linux/if_eql.h>
142 #ifndef EQL_DEBUG
143 /* #undef EQL_DEBUG -* print nothing at all, not even a boot-banner */
144 /* #define EQL_DEBUG 1 -* print only the boot-banner */
145 /* #define EQL_DEBUG 5 -* print major function entries */
146 /* #define EQL_DEBUG 20 -* print subfunction entries */
147 /* #define EQL_DEBUG 50 -* print utility entries */
148 /* #define EQL_DEBUG 100 -* print voluminous function entries */
149 #define EQL_DEBUG 1
150 #endif
151 static unsigned int eql_debug = EQL_DEBUG;
153 int eql_init(struct net_device *dev); /* */
154 static int eql_open(struct net_device *dev); /* */
155 static int eql_close(struct net_device *dev); /* */
156 static int eql_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd); /* */
157 static int eql_slave_xmit(struct sk_buff *skb, struct net_device *dev); /* */
159 static struct net_device_stats *eql_get_stats(struct net_device *dev); /* */
161 /* ioctl() handlers
162 ---------------- */
163 static int eql_enslave(struct net_device *dev, slaving_request_t *srq); /* */
164 static int eql_emancipate(struct net_device *dev, slaving_request_t *srq); /* */
166 static int eql_g_slave_cfg(struct net_device *dev, slave_config_t *sc); /* */
167 static int eql_s_slave_cfg(struct net_device *dev, slave_config_t *sc); /* */
169 static int eql_g_master_cfg(struct net_device *dev, master_config_t *mc); /* */
170 static int eql_s_master_cfg(struct net_device *dev, master_config_t *mc); /* */
172 static inline int eql_is_slave(struct net_device *dev); /* */
173 static inline int eql_is_master(struct net_device *dev); /* */
175 static slave_t *eql_new_slave(void); /* */
176 static void eql_delete_slave(slave_t *slave); /* */
178 /* static long eql_slave_priority(slave_t *slave); -* */
179 static inline int eql_number_slaves(slave_queue_t *queue); /* */
181 static inline int eql_is_empty(slave_queue_t *queue); /* */
182 static inline int eql_is_full(slave_queue_t *queue); /* */
184 static slave_queue_t *eql_new_slave_queue(struct net_device *dev); /* */
185 static void eql_delete_slave_queue(slave_queue_t *queue); /* */
187 static int eql_insert_slave(slave_queue_t *queue, slave_t *slave); /* */
188 static slave_t *eql_remove_slave(slave_queue_t *queue, slave_t *slave); /* */
190 /* static int eql_insert_slave_dev(slave_queue_t *queue, struct net_device *dev); -* */
191 static int eql_remove_slave_dev(slave_queue_t *queue, struct net_device *dev); /* */
193 static inline struct net_device *eql_best_slave_dev(slave_queue_t *queue); /* */
194 static inline slave_t *eql_best_slave(slave_queue_t *queue); /* */
195 static inline slave_t *eql_first_slave(slave_queue_t *queue); /* */
196 static inline slave_t *eql_next_slave(slave_queue_t *queue, slave_t *slave); /* */
198 static inline void eql_set_best_slave(slave_queue_t *queue, slave_t *slave); /* */
199 static inline void eql_schedule_slaves(slave_queue_t *queue); /* */
201 static slave_t *eql_find_slave_dev(slave_queue_t *queue, struct net_device *dev); /* */
203 /* static inline eql_lock_slave_queue(slave_queue_t *queue); -* */
204 /* static inline eql_unlock_slave_queue(slave_queue_t *queue); -* */
206 static void eql_timer(unsigned long param); /* */
208 /* struct net_device * interface functions
209 ---------------------------------------------------------
212 int __init eql_init(struct net_device *dev)
214 static unsigned version_printed = 0;
215 /* static unsigned num_masters = 0; */
216 equalizer_t *eql = 0;
218 if ( version_printed++ == 0 && eql_debug > 0)
219 printk(version);
221 * Initialize the device structure.
223 dev->priv = kmalloc (sizeof (equalizer_t), GFP_KERNEL);
224 if (dev->priv == NULL)
225 return -ENOMEM;
226 memset (dev->priv, 0, sizeof (equalizer_t));
227 eql = (equalizer_t *) dev->priv;
229 eql->stats = kmalloc (sizeof (struct net_device_stats), GFP_KERNEL);
230 if (eql->stats == NULL)
232 kfree(dev->priv);
233 dev->priv = NULL;
234 return -ENOMEM;
236 memset (eql->stats, 0, sizeof (struct net_device_stats));
238 init_timer (&eql->timer);
239 eql->timer.data = (unsigned long) dev->priv;
240 eql->timer.expires = jiffies+EQL_DEFAULT_RESCHED_IVAL;
241 eql->timer.function = &eql_timer;
242 eql->timer_on = 0;
244 dev->open = eql_open;
245 dev->stop = eql_close;
246 dev->do_ioctl = eql_ioctl;
247 dev->hard_start_xmit = eql_slave_xmit;
248 dev->get_stats = eql_get_stats;
251 * Fill in the fields of the device structure with
252 * eql-generic values.
255 dev_init_buffers(dev);
258 * Now we undo some of the things that eth_setup does
259 * that we don't like
262 dev->mtu = EQL_DEFAULT_MTU; /* set to 576 in eql.h */
263 dev->flags = IFF_MASTER;
265 dev->type = ARPHRD_SLIP;
266 dev->tx_queue_len = 5; /* Hands them off fast */
268 return 0;
271 static int eql_open(struct net_device *dev)
273 equalizer_t *eql = (equalizer_t *) dev->priv;
274 slave_queue_t *new_queue;
276 #ifdef EQL_DEBUG
277 if (eql_debug >= 5)
278 printk ("%s: open\n", dev->name);
279 #endif
281 printk ("%s: remember to turn off Van-Jacobson compression on your slave devices.\n", dev->name);
283 new_queue = eql_new_slave_queue (dev);
285 if (new_queue != 0)
287 new_queue->master_dev = dev;
288 eql->queue = new_queue;
289 eql->queue->lock = 0;
290 eql->min_slaves = 1;
291 eql->max_slaves = EQL_DEFAULT_MAX_SLAVES; /* 4 usually... */
293 printk ("%s: adding timer\n", dev->name);
294 eql->timer_on = 1;
295 add_timer (&eql->timer);
297 MOD_INC_USE_COUNT;
298 return 0;
300 return 1;
304 static int eql_close(struct net_device *dev)
306 equalizer_t *eql = (equalizer_t *) dev->priv;
308 #ifdef EQL_DEBUG
309 if ( eql_debug >= 5)
310 printk ("%s: close\n", dev->name);
311 #endif
313 * The timer has to be stopped first before we start hacking away
314 * at the data structure it scans every so often...
317 #ifdef EQL_DEBUG
318 printk ("%s: stopping timer\n", dev->name);
319 #endif
320 eql->timer_on = 0;
321 del_timer (&eql->timer);
323 eql_delete_slave_queue (eql->queue);
325 MOD_DEC_USE_COUNT;
326 return 0;
330 static int eql_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
332 if(cmd!=EQL_GETMASTRCFG && cmd!=EQL_GETSLAVECFG &&
333 !capable(CAP_NET_ADMIN))
334 return -EPERM;
335 switch (cmd)
337 case EQL_ENSLAVE:
338 return eql_enslave (dev, (slaving_request_t *) ifr->ifr_data);
339 case EQL_EMANCIPATE:
340 return eql_emancipate (dev, (slaving_request_t *) ifr->ifr_data);
341 case EQL_GETSLAVECFG:
342 return eql_g_slave_cfg (dev, (slave_config_t *) ifr->ifr_data);
343 case EQL_SETSLAVECFG:
344 return eql_s_slave_cfg (dev, (slave_config_t *) ifr->ifr_data);
345 case EQL_GETMASTRCFG:
346 return eql_g_master_cfg (dev, (master_config_t *) ifr->ifr_data);
347 case EQL_SETMASTRCFG:
348 return eql_s_master_cfg (dev, (master_config_t *) ifr->ifr_data);
349 default:
350 return -EOPNOTSUPP;
355 static int eql_slave_xmit(struct sk_buff *skb, struct net_device *dev)
357 equalizer_t *eql = (equalizer_t *) dev->priv;
358 struct net_device *slave_dev = 0;
359 slave_t *slave;
361 if (skb == NULL)
362 return 0;
364 eql_schedule_slaves (eql->queue);
366 slave = eql_best_slave (eql->queue);
367 slave_dev = slave ? slave->dev : 0;
369 if ( slave_dev != 0 )
371 #ifdef EQL_DEBUG
372 if (eql_debug >= 100)
373 printk ("%s: %d slaves xmitng %d B %s\n",
374 dev->name, eql_number_slaves (eql->queue), skb->len,
375 slave_dev->name);
376 #endif
377 skb->dev = slave_dev;
378 skb->priority = 1;
379 dev_queue_xmit (skb);
380 eql->stats->tx_packets++;
381 slave->bytes_queued += skb->len;
383 else
386 * The alternative for this is the return 1 and have
387 * dev_queue_xmit just queue it up on the eql's queue.
390 eql->stats->tx_dropped++;
391 dev_kfree_skb(skb);
393 return 0;
397 static struct net_device_stats * eql_get_stats(struct net_device *dev)
399 equalizer_t *eql = (equalizer_t *) dev->priv;
400 return eql->stats;
404 * Private ioctl functions
407 static int eql_enslave(struct net_device *dev, slaving_request_t *srqp)
409 struct net_device *master_dev;
410 struct net_device *slave_dev;
411 slaving_request_t srq;
412 int err;
414 err = copy_from_user(&srq, srqp, sizeof (slaving_request_t));
415 if (err)
417 #ifdef EQL_DEBUG
418 if (eql_debug >= 20)
419 printk ("EQL enslave: error detected by copy_from_user\n");
420 #endif
421 return err;
424 #ifdef EQL_DEBUG
425 if (eql_debug >= 20)
426 printk ("%s: enslave '%s' %ld bps\n", dev->name,
427 srq.slave_name, srq.priority);
428 #endif
429 master_dev = dev; /* for "clarity" */
430 slave_dev = __dev_get_by_name (srq.slave_name);
432 if (master_dev != 0 && slave_dev != 0)
434 if ((master_dev->flags & IFF_UP) == IFF_UP)
436 /*slave is not a master & not already a slave:*/
437 if (! eql_is_master (slave_dev) &&
438 ! eql_is_slave (slave_dev) )
440 slave_t *s = eql_new_slave ();
441 equalizer_t *eql =
442 (equalizer_t *) master_dev->priv;
443 s->dev = slave_dev;
444 s->priority = srq.priority;
445 s->priority_bps = srq.priority;
446 s->priority_Bps = srq.priority / 8;
447 slave_dev->flags |= IFF_SLAVE;
448 eql_insert_slave (eql->queue, s);
449 return 0;
451 #ifdef EQL_DEBUG
452 else if (eql_debug >= 20)
453 printk ("EQL enslave: slave is master or slave is already slave\n");
454 #endif
456 #ifdef EQL_DEBUG
457 else if (eql_debug >= 20)
458 printk ("EQL enslave: master device not up!\n");
459 #endif
461 #ifdef EQL_DEBUG
462 else if (eql_debug >= 20)
463 printk ("EQL enslave: master or slave are NULL");
464 #endif
465 return -EINVAL;
468 static int eql_emancipate(struct net_device *dev, slaving_request_t *srqp)
470 struct net_device *master_dev;
471 struct net_device *slave_dev;
472 slaving_request_t srq;
473 int err;
475 err = copy_from_user(&srq, srqp, sizeof (slaving_request_t));
476 if (err)
477 return err;
479 #ifdef EQL_DEBUG
480 if (eql_debug >= 20)
481 printk ("%s: emancipate `%s`\n", dev->name, srq.slave_name);
482 #endif
483 master_dev = dev; /* for "clarity" */
484 slave_dev = __dev_get_by_name (srq.slave_name);
486 if ( eql_is_slave (slave_dev) ) /* really is a slave */
488 equalizer_t *eql = (equalizer_t *) master_dev->priv;
489 slave_dev->flags = slave_dev->flags & ~IFF_SLAVE;
490 eql_remove_slave_dev (eql->queue, slave_dev);
491 return 0;
493 return -EINVAL;
497 static int eql_g_slave_cfg(struct net_device *dev, slave_config_t *scp)
499 slave_t *slave;
500 equalizer_t *eql;
501 struct net_device *slave_dev;
502 slave_config_t sc;
503 int err;
505 err = copy_from_user (&sc, scp, sizeof (slave_config_t));
506 if (err)
507 return err;
509 #ifdef EQL_DEBUG
510 if (eql_debug >= 20)
511 printk ("%s: get config for slave `%s'\n", dev->name, sc.slave_name);
512 #endif
513 eql = (equalizer_t *) dev->priv;
514 slave_dev = __dev_get_by_name (sc.slave_name);
516 if ( eql_is_slave (slave_dev) )
518 slave = eql_find_slave_dev (eql->queue, slave_dev);
519 if (slave != 0)
521 sc.priority = slave->priority;
522 err = verify_area(VERIFY_WRITE, (void *)scp, sizeof (slave_config_t));
523 if (err)
524 return err;
525 copy_to_user (scp, &sc, sizeof (slave_config_t));
526 return 0;
529 return -EINVAL;
533 static int eql_s_slave_cfg(struct net_device *dev, slave_config_t *scp)
535 slave_t *slave;
536 equalizer_t *eql;
537 struct net_device *slave_dev;
538 slave_config_t sc;
539 int err;
541 err = copy_from_user (&sc, scp, sizeof (slave_config_t));
542 if (err)
543 return err;
545 #ifdef EQL_DEBUG
546 if (eql_debug >= 20)
547 printk ("%s: set config for slave `%s'\n", dev->name, sc.slave_name);
548 #endif
551 eql = (equalizer_t *) dev->priv;
552 slave_dev = __dev_get_by_name (sc.slave_name);
554 if ( eql_is_slave (slave_dev) )
556 slave = eql_find_slave_dev (eql->queue, slave_dev);
557 if (slave != 0)
559 slave->priority = sc.priority;
560 slave->priority_bps = sc.priority;
561 slave->priority_Bps = sc.priority / 8;
562 return 0;
565 return -EINVAL;
569 static int eql_g_master_cfg(struct net_device *dev, master_config_t *mcp)
571 equalizer_t *eql;
572 master_config_t mc;
574 #if EQL_DEBUG
575 if (eql_debug >= 20)
576 printk ("%s: get master config\n", dev->name);
577 #endif
579 if ( eql_is_master (dev) )
581 int err;
582 eql = (equalizer_t *) dev->priv;
583 mc.max_slaves = eql->max_slaves;
584 mc.min_slaves = eql->min_slaves;
585 err = copy_to_user (mcp, &mc, sizeof (master_config_t));
586 if (err)
587 return err;
588 return 0;
590 return -EINVAL;
594 static int eql_s_master_cfg(struct net_device *dev, master_config_t *mcp)
596 equalizer_t *eql;
597 master_config_t mc;
598 int err;
600 err = copy_from_user (&mc, mcp, sizeof (master_config_t));
601 if (err)
602 return err;
603 #if EQL_DEBUG
604 if (eql_debug >= 20)
605 printk ("%s: set master config\n", dev->name);
606 #endif
607 if ( eql_is_master (dev) )
609 eql = (equalizer_t *) dev->priv;
610 eql->max_slaves = mc.max_slaves;
611 eql->min_slaves = mc.min_slaves;
612 return 0;
614 return -EINVAL;
618 * Private device support functions
621 static inline int eql_is_slave(struct net_device *dev)
623 if (dev)
625 if ((dev->flags & IFF_SLAVE) == IFF_SLAVE)
626 return 1;
628 return 0;
632 static inline int eql_is_master(struct net_device *dev)
634 if (dev)
636 if ((dev->flags & IFF_MASTER) == IFF_MASTER)
637 return 1;
639 return 0;
643 static slave_t *eql_new_slave(void)
645 slave_t *slave;
647 slave = (slave_t *) kmalloc (sizeof (slave_t), GFP_KERNEL);
648 if (slave)
650 memset(slave, 0, sizeof (slave_t));
651 return slave;
653 return 0;
657 static void eql_delete_slave(slave_t *slave)
659 kfree (slave);
663 #if 0 /* not currently used, will be used
664 when we really use a priority queue */
665 static long slave_Bps(slave_t *slave)
667 return (slave->priority_Bps);
670 static long slave_bps(slave_t *slave)
672 return (slave->priority_bps);
675 #endif
677 static inline int eql_number_slaves(slave_queue_t *queue)
679 return queue->num_slaves;
682 static inline int eql_is_empty(slave_queue_t *queue)
684 if (eql_number_slaves (queue) == 0)
685 return 1;
686 return 0;
689 static inline int eql_is_full(slave_queue_t *queue)
691 equalizer_t *eql = (equalizer_t *) queue->master_dev->priv;
693 if (eql_number_slaves (queue) == eql->max_slaves)
694 return 1;
695 return 0;
698 static slave_queue_t *eql_new_slave_queue(struct net_device *dev)
700 slave_queue_t *queue;
701 slave_t *head_slave;
702 slave_t *tail_slave;
704 queue = (slave_queue_t *) kmalloc (sizeof (slave_queue_t), GFP_KERNEL);
705 if (queue == NULL)
706 return 0;
707 memset (queue, 0, sizeof (slave_queue_t));
708 head_slave = eql_new_slave ();
709 tail_slave = eql_new_slave ();
711 if ( head_slave != 0 &&
712 tail_slave != 0 )
714 head_slave->next = tail_slave;
715 tail_slave->next = 0;
716 queue->head = head_slave;
717 queue->num_slaves = 0;
718 queue->master_dev = dev;
720 else
722 if (head_slave)
723 kfree(head_slave);
724 if (tail_slave)
725 kfree(tail_slave);
726 kfree (queue);
727 return 0;
729 return queue;
733 static void eql_delete_slave_queue(slave_queue_t *queue)
735 slave_t *zapped;
737 * This should only be called when there isn't a
738 * timer running that scans the data periodically..
739 * dev_close stops the timer...
742 while ( ! eql_is_empty (queue) )
744 zapped = eql_remove_slave (queue, queue->head->next);
745 eql_delete_slave (zapped);
747 kfree (queue->head->next);
748 kfree (queue->head);
749 kfree (queue);
752 static int eql_insert_slave(slave_queue_t *queue, slave_t *slave)
754 cli ();
756 if ( ! eql_is_full (queue) )
758 slave_t *duplicate_slave = 0;
759 duplicate_slave = eql_find_slave_dev (queue, slave->dev);
760 if (duplicate_slave != 0)
762 /* printk ("%s: found a duplicate, killing it and replacing\n",
763 queue->master_dev->name); */
764 eql_delete_slave (eql_remove_slave (queue, duplicate_slave));
766 slave->next = queue->head->next;
767 queue->head->next = slave;
768 queue->num_slaves++;
769 sti ();
770 return 0;
772 sti ();
773 return 1;
777 static slave_t *eql_remove_slave(slave_queue_t *queue, slave_t *slave)
779 slave_t *prev;
780 slave_t *curr;
782 cli ();
784 prev = queue->head;
785 curr = queue->head->next;
786 while (curr != slave &&
787 curr->dev != 0 )
789 /* printk ("%s: remove_slave; searching...\n", queue->master_dev->name); */
790 prev = curr;
791 curr = curr->next;
794 if (curr == slave)
796 prev->next = curr->next;
797 queue->num_slaves--;
798 curr->dev->flags = curr->dev->flags & ~IFF_SLAVE;
799 sti();
800 return curr;
802 sti ();
803 return 0; /* not found */
807 static int eql_remove_slave_dev(slave_queue_t *queue, struct net_device *dev)
809 slave_t *prev;
810 slave_t *curr;
811 slave_t *target;
813 target = eql_find_slave_dev (queue, dev);
815 if (target != 0)
817 cli ();
818 prev = queue->head;
819 curr = prev->next;
820 while (curr != target)
822 prev = curr;
823 curr = curr->next;
825 prev->next = curr->next;
826 queue->num_slaves--;
827 sti ();
828 eql_delete_slave (curr);
829 return 0;
831 return 1;
835 static inline struct net_device *eql_best_slave_dev(slave_queue_t *queue)
837 if (queue->best_slave != 0)
839 if (queue->best_slave->dev != 0)
840 return queue->best_slave->dev;
841 else
842 return 0;
844 else
845 return 0;
849 static inline slave_t *eql_best_slave(slave_queue_t *queue)
851 return queue->best_slave;
854 static inline void eql_schedule_slaves(slave_queue_t *queue)
856 struct net_device *master_dev = queue->master_dev;
857 slave_t *best_slave = 0;
858 slave_t *slave_corpse = 0;
860 #ifdef EQL_DEBUG
861 if (eql_debug >= 100)
862 printk ("%s: schedule %d slaves\n",
863 master_dev->name, eql_number_slaves (queue));
864 #endif
865 if ( eql_is_empty (queue) )
868 * No slaves to play with
870 eql_set_best_slave (queue, (slave_t *) 0);
871 return;
873 else
876 * Make a pass to set the best slave
878 unsigned long best_load = (unsigned long) ULONG_MAX;
879 slave_t *slave = 0;
880 int i;
882 cli ();
883 for (i = 1, slave = eql_first_slave (queue);
884 i <= eql_number_slaves (queue);
885 i++, slave = eql_next_slave (queue, slave))
888 * Go through the slave list once, updating best_slave
889 * whenever a new best_load is found, whenever a dead
890 * slave is found, it is marked to be pulled out of the
891 * queue
894 unsigned long slave_load;
895 unsigned long bytes_queued;
896 unsigned long priority_Bps;
898 if (slave != 0)
900 bytes_queued = slave->bytes_queued;
901 priority_Bps = slave->priority_Bps;
902 if ( slave->dev != 0)
904 if ((slave->dev->flags & IFF_UP) == IFF_UP )
906 slave_load = (ULONG_MAX - (ULONG_MAX / 2)) -
907 (priority_Bps) + bytes_queued * 8;
909 if (slave_load < best_load)
911 best_load = slave_load;
912 best_slave = slave;
915 else /* we found a dead slave */
918 * We only bury one slave at a time, if more than
919 * one slave dies, we will bury him on the next
920 * reschedule. slaves don't die all at once that
921 * much anyway
923 slave_corpse = slave;
927 } /* for */
928 sti ();
929 eql_set_best_slave (queue, best_slave);
930 } /* else */
931 if (slave_corpse != 0)
933 printk ("eql: scheduler found dead slave, burying...\n");
934 eql_delete_slave (eql_remove_slave (queue, slave_corpse));
936 return;
940 static slave_t * eql_find_slave_dev(slave_queue_t *queue, struct net_device *dev)
942 slave_t *slave = 0;
943 slave = eql_first_slave(queue);
945 while (slave != 0 && slave->dev != dev && slave != 0)
947 #if 0
948 if (slave->dev != 0)
949 printk ("eql: find_slave_dev; looked at '%s'...\n", slave->dev->name);
950 else
951 printk ("eql: find_slave_dev; looked at nothing...\n");
952 #endif
953 slave = slave->next;
955 return slave;
959 static inline slave_t *eql_first_slave(slave_queue_t *queue)
961 return queue->head->next;
965 static inline slave_t *eql_next_slave(slave_queue_t *queue, slave_t *slave)
967 return slave->next;
970 static inline void eql_set_best_slave(slave_queue_t *queue, slave_t *slave)
972 queue->best_slave = slave;
975 static void eql_timer(unsigned long param)
977 equalizer_t *eql = (equalizer_t *) param;
978 slave_t *slave;
979 slave_t *slave_corpse = 0;
980 int i;
982 if ( ! eql_is_empty (eql->queue) )
984 cli ();
985 for (i = 1, slave = eql_first_slave (eql->queue);
986 i <= eql_number_slaves (eql->queue);
987 i++, slave = eql_next_slave (eql->queue, slave))
989 if (slave != 0)
991 if ((slave->dev->flags & IFF_UP) == IFF_UP )
993 slave->bytes_queued -= slave->priority_Bps;
994 if (slave->bytes_queued < 0)
995 slave->bytes_queued = 0;
997 else
998 slave_corpse = slave;
1001 sti ();
1002 if (slave_corpse != 0)
1004 printk ("eql: timer found dead slave, burying...\n");
1005 eql_delete_slave (eql_remove_slave (eql->queue, slave_corpse));
1009 if (eql->timer_on != 0)
1011 eql->timer.expires = jiffies+EQL_DEFAULT_RESCHED_IVAL;
1012 add_timer (&eql->timer);
1016 #ifdef MODULE
1017 static struct net_device dev_eql =
1019 "eql", 0, 0, 0, 0, 0, 0, 0, 0, 0, NULL, eql_init
1022 int init_module(void)
1024 if (register_netdev(&dev_eql) != 0) {
1025 printk("eql: register_netdev() returned non-zero.\n");
1026 return -EIO;
1028 return 0;
1031 void cleanup_module(void)
1033 kfree(((equalizer_t *)dev_eql.priv)->stats );
1034 kfree(dev_eql.priv);
1035 unregister_netdev(&dev_eql);
1037 #endif /* MODULE */
1040 * Local Variables:
1041 * compile-command: "gcc -D__KERNEL__ -I/usr/src/linux/net/inet -Wall -Wstrict-prototypes -O6 -m486 -c eql.c"
1042 * version-control: t
1043 * kept-new-versions: 20
1044 * End: