aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/ppp_generic.c
diff options
context:
space:
mode:
authorDavid S. Miller <davem@davemloft.net>2010-12-08 16:15:38 -0500
committerDavid S. Miller <davem@davemloft.net>2010-12-08 16:47:38 -0500
commitfe6c791570efe717946ea7b7dd50aec96b70d551 (patch)
tree1becb5e8aea7a9c9a7d78f987bd73b0a5d8ee434 /drivers/net/ppp_generic.c
parentf8bf5681cf15f77692c8ad8cb95d059ff7c622c9 (diff)
parentf19872575ff7819a3723154657a497d9bca66b33 (diff)
Merge branch 'master' of master.kernel.org:/pub/scm/linux/kernel/git/davem/net-2.6
Conflicts: drivers/net/wireless/ath/ath9k/ar9003_eeprom.c net/llc/af_llc.c
Diffstat (limited to 'drivers/net/ppp_generic.c')
-rw-r--r--drivers/net/ppp_generic.c43
1 files changed, 22 insertions, 21 deletions
diff --git a/drivers/net/ppp_generic.c b/drivers/net/ppp_generic.c
index 0c91598ae280..b708f68471a6 100644
--- a/drivers/net/ppp_generic.c
+++ b/drivers/net/ppp_generic.c
@@ -2580,16 +2580,16 @@ ppp_create_interface(struct net *net, int unit, int *retp)
2580 */ 2580 */
2581 dev_net_set(dev, net); 2581 dev_net_set(dev, net);
2582 2582
2583 ret = -EEXIST;
2584 mutex_lock(&pn->all_ppp_mutex); 2583 mutex_lock(&pn->all_ppp_mutex);
2585 2584
2586 if (unit < 0) { 2585 if (unit < 0) {
2587 unit = unit_get(&pn->units_idr, ppp); 2586 unit = unit_get(&pn->units_idr, ppp);
2588 if (unit < 0) { 2587 if (unit < 0) {
2589 *retp = unit; 2588 ret = unit;
2590 goto out2; 2589 goto out2;
2591 } 2590 }
2592 } else { 2591 } else {
2592 ret = -EEXIST;
2593 if (unit_find(&pn->units_idr, unit)) 2593 if (unit_find(&pn->units_idr, unit))
2594 goto out2; /* unit already exists */ 2594 goto out2; /* unit already exists */
2595 /* 2595 /*
@@ -2664,10 +2664,10 @@ static void ppp_shutdown_interface(struct ppp *ppp)
2664 ppp->closing = 1; 2664 ppp->closing = 1;
2665 ppp_unlock(ppp); 2665 ppp_unlock(ppp);
2666 unregister_netdev(ppp->dev); 2666 unregister_netdev(ppp->dev);
2667 unit_put(&pn->units_idr, ppp->file.index);
2667 } else 2668 } else
2668 ppp_unlock(ppp); 2669 ppp_unlock(ppp);
2669 2670
2670 unit_put(&pn->units_idr, ppp->file.index);
2671 ppp->file.dead = 1; 2671 ppp->file.dead = 1;
2672 ppp->owner = NULL; 2672 ppp->owner = NULL;
2673 wake_up_interruptible(&ppp->file.rwait); 2673 wake_up_interruptible(&ppp->file.rwait);
@@ -2855,8 +2855,7 @@ static void __exit ppp_cleanup(void)
2855 * by holding all_ppp_mutex 2855 * by holding all_ppp_mutex
2856 */ 2856 */
2857 2857
2858/* associate pointer with specified number */ 2858static int __unit_alloc(struct idr *p, void *ptr, int n)
2859static int unit_set(struct idr *p, void *ptr, int n)
2860{ 2859{
2861 int unit, err; 2860 int unit, err;
2862 2861
@@ -2867,10 +2866,24 @@ again:
2867 } 2866 }
2868 2867
2869 err = idr_get_new_above(p, ptr, n, &unit); 2868 err = idr_get_new_above(p, ptr, n, &unit);
2870 if (err == -EAGAIN) 2869 if (err < 0) {
2871 goto again; 2870 if (err == -EAGAIN)
2871 goto again;
2872 return err;
2873 }
2874
2875 return unit;
2876}
2877
2878/* associate pointer with specified number */
2879static int unit_set(struct idr *p, void *ptr, int n)
2880{
2881 int unit;
2872 2882
2873 if (unit != n) { 2883 unit = __unit_alloc(p, ptr, n);
2884 if (unit < 0)
2885 return unit;
2886 else if (unit != n) {
2874 idr_remove(p, unit); 2887 idr_remove(p, unit);
2875 return -EINVAL; 2888 return -EINVAL;
2876 } 2889 }
@@ -2881,19 +2894,7 @@ again:
2881/* get new free unit number and associate pointer with it */ 2894/* get new free unit number and associate pointer with it */
2882static int unit_get(struct idr *p, void *ptr) 2895static int unit_get(struct idr *p, void *ptr)
2883{ 2896{
2884 int unit, err; 2897 return __unit_alloc(p, ptr, 0);
2885
2886again:
2887 if (!idr_pre_get(p, GFP_KERNEL)) {
2888 printk(KERN_ERR "PPP: No free memory for idr\n");
2889 return -ENOMEM;
2890 }
2891
2892 err = idr_get_new_above(p, ptr, 0, &unit);
2893 if (err == -EAGAIN)
2894 goto again;
2895
2896 return unit;
2897} 2898}
2898 2899
2899/* put unit number back to a pool */ 2900/* put unit number back to a pool */