diff options
Diffstat (limited to 'net')
-rw-r--r-- | net/bluetooth/hidp/Kconfig | 1 | ||||
-rw-r--r-- | net/bluetooth/hidp/core.c | 182 | ||||
-rw-r--r-- | net/bluetooth/hidp/hidp.h | 2 | ||||
-rw-r--r-- | net/bluetooth/hidp/sock.c | 2 | ||||
-rw-r--r-- | net/bluetooth/rfcomm/tty.c | 9 | ||||
-rw-r--r-- | net/bridge/br_if.c | 30 | ||||
-rw-r--r-- | net/bridge/br_notify.c | 25 | ||||
-rw-r--r-- | net/bridge/br_private.h | 5 | ||||
-rw-r--r-- | net/bridge/netfilter/ebtables.c | 9 | ||||
-rw-r--r-- | net/ipv4/Kconfig | 4 | ||||
-rw-r--r-- | net/ipv4/devinet.c | 8 | ||||
-rw-r--r-- | net/ipv4/multipath_random.c | 18 | ||||
-rw-r--r-- | net/ipv4/multipath_wrandom.c | 15 | ||||
-rw-r--r-- | net/ipv4/tcp.c | 24 | ||||
-rw-r--r-- | net/ipv4/xfrm4_mode_tunnel.c | 1 | ||||
-rw-r--r-- | net/ipv4/xfrm4_policy.c | 2 | ||||
-rw-r--r-- | net/ipv6/Makefile | 2 | ||||
-rw-r--r-- | net/ipv6/addrconf.c | 98 | ||||
-rw-r--r-- | net/ipv6/addrconf_core.c | 76 | ||||
-rw-r--r-- | net/ipv6/af_inet6.c | 24 | ||||
-rw-r--r-- | net/ipv6/ip6_tunnel.c | 7 | ||||
-rw-r--r-- | net/ipv6/ipv6_syms.c | 1 | ||||
-rw-r--r-- | net/ipv6/xfrm6_policy.c | 2 | ||||
-rw-r--r-- | net/irda/irmod.c | 13 | ||||
-rw-r--r-- | net/packet/af_packet.c | 13 | ||||
-rw-r--r-- | net/sctp/outqueue.c | 27 | ||||
-rw-r--r-- | net/sctp/sm_statefuns.c | 6 | ||||
-rw-r--r-- | net/sunrpc/svc.c | 4 |
28 files changed, 378 insertions, 232 deletions
diff --git a/net/bluetooth/hidp/Kconfig b/net/bluetooth/hidp/Kconfig index c6abf2a5a932..98fdfa1fbddd 100644 --- a/net/bluetooth/hidp/Kconfig +++ b/net/bluetooth/hidp/Kconfig | |||
@@ -1,6 +1,7 @@ | |||
1 | config BT_HIDP | 1 | config BT_HIDP |
2 | tristate "HIDP protocol support" | 2 | tristate "HIDP protocol support" |
3 | depends on BT && BT_L2CAP && INPUT | 3 | depends on BT && BT_L2CAP && INPUT |
4 | select HID | ||
4 | help | 5 | help |
5 | HIDP (Human Interface Device Protocol) is a transport layer | 6 | HIDP (Human Interface Device Protocol) is a transport layer |
6 | for HID reports. HIDP is required for the Bluetooth Human | 7 | for HID reports. HIDP is required for the Bluetooth Human |
diff --git a/net/bluetooth/hidp/core.c b/net/bluetooth/hidp/core.c index 4b99c5e4478d..4c914df5fd06 100644 --- a/net/bluetooth/hidp/core.c +++ b/net/bluetooth/hidp/core.c | |||
@@ -38,6 +38,7 @@ | |||
38 | #include <net/sock.h> | 38 | #include <net/sock.h> |
39 | 39 | ||
40 | #include <linux/input.h> | 40 | #include <linux/input.h> |
41 | #include <linux/hid.h> | ||
41 | 42 | ||
42 | #include <net/bluetooth/bluetooth.h> | 43 | #include <net/bluetooth/bluetooth.h> |
43 | #include <net/bluetooth/hci_core.h> | 44 | #include <net/bluetooth/hci_core.h> |
@@ -50,7 +51,7 @@ | |||
50 | #define BT_DBG(D...) | 51 | #define BT_DBG(D...) |
51 | #endif | 52 | #endif |
52 | 53 | ||
53 | #define VERSION "1.1" | 54 | #define VERSION "1.2" |
54 | 55 | ||
55 | static DECLARE_RWSEM(hidp_session_sem); | 56 | static DECLARE_RWSEM(hidp_session_sem); |
56 | static LIST_HEAD(hidp_session_list); | 57 | static LIST_HEAD(hidp_session_list); |
@@ -124,15 +125,22 @@ static void __hidp_copy_session(struct hidp_session *session, struct hidp_connin | |||
124 | else | 125 | else |
125 | strncpy(ci->name, "HID Boot Device", 128); | 126 | strncpy(ci->name, "HID Boot Device", 128); |
126 | } | 127 | } |
128 | |||
129 | if (session->hid) { | ||
130 | ci->vendor = session->hid->vendor; | ||
131 | ci->product = session->hid->product; | ||
132 | ci->version = session->hid->version; | ||
133 | strncpy(ci->name, session->hid->name, 128); | ||
134 | } | ||
127 | } | 135 | } |
128 | 136 | ||
129 | static int hidp_input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value) | 137 | static inline int hidp_queue_event(struct hidp_session *session, struct input_dev *dev, |
138 | unsigned int type, unsigned int code, int value) | ||
130 | { | 139 | { |
131 | struct hidp_session *session = dev->private; | ||
132 | struct sk_buff *skb; | ||
133 | unsigned char newleds; | 140 | unsigned char newleds; |
141 | struct sk_buff *skb; | ||
134 | 142 | ||
135 | BT_DBG("input %p type %d code %d value %d", dev, type, code, value); | 143 | BT_DBG("session %p type %d code %d value %d", session, type, code, value); |
136 | 144 | ||
137 | if (type != EV_LED) | 145 | if (type != EV_LED) |
138 | return -1; | 146 | return -1; |
@@ -164,6 +172,21 @@ static int hidp_input_event(struct input_dev *dev, unsigned int type, unsigned i | |||
164 | return 0; | 172 | return 0; |
165 | } | 173 | } |
166 | 174 | ||
175 | static int hidp_hidinput_event(struct input_dev *dev, unsigned int type, unsigned int code, int value) | ||
176 | { | ||
177 | struct hid_device *hid = dev->private; | ||
178 | struct hidp_session *session = hid->driver_data; | ||
179 | |||
180 | return hidp_queue_event(session, dev, type, code, value); | ||
181 | } | ||
182 | |||
183 | static int hidp_input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value) | ||
184 | { | ||
185 | struct hidp_session *session = dev->private; | ||
186 | |||
187 | return hidp_queue_event(session, dev, type, code, value); | ||
188 | } | ||
189 | |||
167 | static void hidp_input_report(struct hidp_session *session, struct sk_buff *skb) | 190 | static void hidp_input_report(struct hidp_session *session, struct sk_buff *skb) |
168 | { | 191 | { |
169 | struct input_dev *dev = session->input; | 192 | struct input_dev *dev = session->input; |
@@ -219,6 +242,42 @@ static void hidp_input_report(struct hidp_session *session, struct sk_buff *skb) | |||
219 | input_sync(dev); | 242 | input_sync(dev); |
220 | } | 243 | } |
221 | 244 | ||
245 | static inline int hidp_queue_report(struct hidp_session *session, unsigned char *data, int size) | ||
246 | { | ||
247 | struct sk_buff *skb; | ||
248 | |||
249 | BT_DBG("session %p hid %p data %p size %d", session, device, data, size); | ||
250 | |||
251 | if (!(skb = alloc_skb(size + 1, GFP_ATOMIC))) { | ||
252 | BT_ERR("Can't allocate memory for new frame"); | ||
253 | return -ENOMEM; | ||
254 | } | ||
255 | |||
256 | *skb_put(skb, 1) = 0xa2; | ||
257 | if (size > 0) | ||
258 | memcpy(skb_put(skb, size), data, size); | ||
259 | |||
260 | skb_queue_tail(&session->intr_transmit, skb); | ||
261 | |||
262 | hidp_schedule(session); | ||
263 | |||
264 | return 0; | ||
265 | } | ||
266 | |||
267 | static int hidp_send_report(struct hidp_session *session, struct hid_report *report) | ||
268 | { | ||
269 | unsigned char buf[32]; | ||
270 | int rsize; | ||
271 | |||
272 | rsize = ((report->size - 1) >> 3) + 1 + (report->id > 0); | ||
273 | if (rsize > sizeof(buf)) | ||
274 | return -EIO; | ||
275 | |||
276 | hid_output_report(report, buf); | ||
277 | |||
278 | return hidp_queue_report(session, buf, rsize); | ||
279 | } | ||
280 | |||
222 | static void hidp_idle_timeout(unsigned long arg) | 281 | static void hidp_idle_timeout(unsigned long arg) |
223 | { | 282 | { |
224 | struct hidp_session *session = (struct hidp_session *) arg; | 283 | struct hidp_session *session = (struct hidp_session *) arg; |
@@ -346,6 +405,10 @@ static inline void hidp_process_data(struct hidp_session *session, struct sk_buf | |||
346 | 405 | ||
347 | if (session->input) | 406 | if (session->input) |
348 | hidp_input_report(session, skb); | 407 | hidp_input_report(session, skb); |
408 | |||
409 | if (session->hid) | ||
410 | hid_input_report(session->hid, HID_INPUT_REPORT, skb->data, skb->len, 0); | ||
411 | |||
349 | break; | 412 | break; |
350 | 413 | ||
351 | case HIDP_DATA_RTYPE_OTHER: | 414 | case HIDP_DATA_RTYPE_OTHER: |
@@ -404,8 +467,14 @@ static inline void hidp_recv_intr_frame(struct hidp_session *session, struct sk_ | |||
404 | 467 | ||
405 | if (hdr == (HIDP_TRANS_DATA | HIDP_DATA_RTYPE_INPUT)) { | 468 | if (hdr == (HIDP_TRANS_DATA | HIDP_DATA_RTYPE_INPUT)) { |
406 | hidp_set_timer(session); | 469 | hidp_set_timer(session); |
470 | |||
407 | if (session->input) | 471 | if (session->input) |
408 | hidp_input_report(session, skb); | 472 | hidp_input_report(session, skb); |
473 | |||
474 | if (session->hid) { | ||
475 | hid_input_report(session->hid, HID_INPUT_REPORT, skb->data, skb->len, 1); | ||
476 | BT_DBG("report len %d", skb->len); | ||
477 | } | ||
409 | } else { | 478 | } else { |
410 | BT_DBG("Unsupported protocol header 0x%02x", hdr); | 479 | BT_DBG("Unsupported protocol header 0x%02x", hdr); |
411 | } | 480 | } |
@@ -471,6 +540,11 @@ static int hidp_session(void *arg) | |||
471 | product = session->input->id.product; | 540 | product = session->input->id.product; |
472 | } | 541 | } |
473 | 542 | ||
543 | if (session->hid) { | ||
544 | vendor = session->hid->vendor; | ||
545 | product = session->hid->product; | ||
546 | } | ||
547 | |||
474 | daemonize("khidpd_%04x%04x", vendor, product); | 548 | daemonize("khidpd_%04x%04x", vendor, product); |
475 | set_user_nice(current, -15); | 549 | set_user_nice(current, -15); |
476 | current->flags |= PF_NOFREEZE; | 550 | current->flags |= PF_NOFREEZE; |
@@ -521,6 +595,12 @@ static int hidp_session(void *arg) | |||
521 | session->input = NULL; | 595 | session->input = NULL; |
522 | } | 596 | } |
523 | 597 | ||
598 | if (session->hid) { | ||
599 | if (session->hid->claimed & HID_CLAIMED_INPUT) | ||
600 | hidinput_disconnect(session->hid); | ||
601 | hid_free_device(session->hid); | ||
602 | } | ||
603 | |||
524 | up_write(&hidp_session_sem); | 604 | up_write(&hidp_session_sem); |
525 | 605 | ||
526 | kfree(session); | 606 | kfree(session); |
@@ -590,6 +670,56 @@ static inline void hidp_setup_input(struct hidp_session *session, struct hidp_co | |||
590 | input_register_device(input); | 670 | input_register_device(input); |
591 | } | 671 | } |
592 | 672 | ||
673 | static int hidp_open(struct hid_device *hid) | ||
674 | { | ||
675 | return 0; | ||
676 | } | ||
677 | |||
678 | static void hidp_close(struct hid_device *hid) | ||
679 | { | ||
680 | } | ||
681 | |||
682 | static inline void hidp_setup_hid(struct hidp_session *session, struct hidp_connadd_req *req) | ||
683 | { | ||
684 | struct hid_device *hid = session->hid; | ||
685 | struct hid_report *report; | ||
686 | bdaddr_t src, dst; | ||
687 | |||
688 | baswap(&src, &bt_sk(session->ctrl_sock->sk)->src); | ||
689 | baswap(&dst, &bt_sk(session->ctrl_sock->sk)->dst); | ||
690 | |||
691 | hid->driver_data = session; | ||
692 | |||
693 | hid->country = req->country; | ||
694 | |||
695 | hid->bus = BUS_BLUETOOTH; | ||
696 | hid->vendor = req->vendor; | ||
697 | hid->product = req->product; | ||
698 | hid->version = req->version; | ||
699 | |||
700 | strncpy(hid->name, req->name, 128); | ||
701 | strncpy(hid->phys, batostr(&src), 64); | ||
702 | strncpy(hid->uniq, batostr(&dst), 64); | ||
703 | |||
704 | hid->dev = hidp_get_device(session); | ||
705 | |||
706 | hid->hid_open = hidp_open; | ||
707 | hid->hid_close = hidp_close; | ||
708 | |||
709 | hid->hidinput_input_event = hidp_hidinput_event; | ||
710 | |||
711 | list_for_each_entry(report, &hid->report_enum[HID_INPUT_REPORT].report_list, list) | ||
712 | hidp_send_report(session, report); | ||
713 | |||
714 | list_for_each_entry(report, &hid->report_enum[HID_FEATURE_REPORT].report_list, list) | ||
715 | hidp_send_report(session, report); | ||
716 | |||
717 | if (hidinput_connect(hid) == 0) { | ||
718 | hid->claimed |= HID_CLAIMED_INPUT; | ||
719 | hid_ff_init(hid); | ||
720 | } | ||
721 | } | ||
722 | |||
593 | int hidp_add_connection(struct hidp_connadd_req *req, struct socket *ctrl_sock, struct socket *intr_sock) | 723 | int hidp_add_connection(struct hidp_connadd_req *req, struct socket *ctrl_sock, struct socket *intr_sock) |
594 | { | 724 | { |
595 | struct hidp_session *session, *s; | 725 | struct hidp_session *session, *s; |
@@ -605,10 +735,38 @@ int hidp_add_connection(struct hidp_connadd_req *req, struct socket *ctrl_sock, | |||
605 | if (!session) | 735 | if (!session) |
606 | return -ENOMEM; | 736 | return -ENOMEM; |
607 | 737 | ||
608 | session->input = input_allocate_device(); | 738 | BT_DBG("rd_data %p rd_size %d", req->rd_data, req->rd_size); |
609 | if (!session->input) { | 739 | |
610 | kfree(session); | 740 | if (req->rd_size > 0) { |
611 | return -ENOMEM; | 741 | unsigned char *buf = kmalloc(req->rd_size, GFP_KERNEL); |
742 | |||
743 | if (!buf) { | ||
744 | kfree(session); | ||
745 | return -ENOMEM; | ||
746 | } | ||
747 | |||
748 | if (copy_from_user(buf, req->rd_data, req->rd_size)) { | ||
749 | kfree(buf); | ||
750 | kfree(session); | ||
751 | return -EFAULT; | ||
752 | } | ||
753 | |||
754 | session->hid = hid_parse_report(buf, req->rd_size); | ||
755 | |||
756 | kfree(buf); | ||
757 | |||
758 | if (!session->hid) { | ||
759 | kfree(session); | ||
760 | return -EINVAL; | ||
761 | } | ||
762 | } | ||
763 | |||
764 | if (!session->hid) { | ||
765 | session->input = input_allocate_device(); | ||
766 | if (!session->input) { | ||
767 | kfree(session); | ||
768 | return -ENOMEM; | ||
769 | } | ||
612 | } | 770 | } |
613 | 771 | ||
614 | down_write(&hidp_session_sem); | 772 | down_write(&hidp_session_sem); |
@@ -644,6 +802,9 @@ int hidp_add_connection(struct hidp_connadd_req *req, struct socket *ctrl_sock, | |||
644 | if (session->input) | 802 | if (session->input) |
645 | hidp_setup_input(session, req); | 803 | hidp_setup_input(session, req); |
646 | 804 | ||
805 | if (session->hid) | ||
806 | hidp_setup_hid(session, req); | ||
807 | |||
647 | __hidp_link_session(session); | 808 | __hidp_link_session(session); |
648 | 809 | ||
649 | hidp_set_timer(session); | 810 | hidp_set_timer(session); |
@@ -677,6 +838,9 @@ unlink: | |||
677 | failed: | 838 | failed: |
678 | up_write(&hidp_session_sem); | 839 | up_write(&hidp_session_sem); |
679 | 840 | ||
841 | if (session->hid) | ||
842 | hid_free_device(session->hid); | ||
843 | |||
680 | kfree(session->input); | 844 | kfree(session->input); |
681 | kfree(session); | 845 | kfree(session); |
682 | return err; | 846 | return err; |
diff --git a/net/bluetooth/hidp/hidp.h b/net/bluetooth/hidp/hidp.h index a326601c8f41..343fb0566b3e 100644 --- a/net/bluetooth/hidp/hidp.h +++ b/net/bluetooth/hidp/hidp.h | |||
@@ -145,6 +145,8 @@ struct hidp_session { | |||
145 | 145 | ||
146 | struct input_dev *input; | 146 | struct input_dev *input; |
147 | 147 | ||
148 | struct hid_device *hid; | ||
149 | |||
148 | struct timer_list timer; | 150 | struct timer_list timer; |
149 | 151 | ||
150 | struct sk_buff_head ctrl_transmit; | 152 | struct sk_buff_head ctrl_transmit; |
diff --git a/net/bluetooth/hidp/sock.c b/net/bluetooth/hidp/sock.c index 8b8a6c1dbd99..0c185257e55b 100644 --- a/net/bluetooth/hidp/sock.c +++ b/net/bluetooth/hidp/sock.c | |||
@@ -194,7 +194,7 @@ static int hidp_sock_compat_ioctl(struct socket *sock, unsigned int cmd, unsigne | |||
194 | if (put_user(ca.ctrl_sock, &uca->ctrl_sock) || | 194 | if (put_user(ca.ctrl_sock, &uca->ctrl_sock) || |
195 | put_user(ca.intr_sock, &uca->intr_sock) || | 195 | put_user(ca.intr_sock, &uca->intr_sock) || |
196 | put_user(ca.parser, &uca->parser) || | 196 | put_user(ca.parser, &uca->parser) || |
197 | put_user(ca.rd_size, &uca->parser) || | 197 | put_user(ca.rd_size, &uca->rd_size) || |
198 | put_user(compat_ptr(ca.rd_data), &uca->rd_data) || | 198 | put_user(compat_ptr(ca.rd_data), &uca->rd_data) || |
199 | put_user(ca.country, &uca->country) || | 199 | put_user(ca.country, &uca->country) || |
200 | put_user(ca.subclass, &uca->subclass) || | 200 | put_user(ca.subclass, &uca->subclass) || |
diff --git a/net/bluetooth/rfcomm/tty.c b/net/bluetooth/rfcomm/tty.c index 8cd82dce5008..9a7a44fc721f 100644 --- a/net/bluetooth/rfcomm/tty.c +++ b/net/bluetooth/rfcomm/tty.c | |||
@@ -74,6 +74,8 @@ struct rfcomm_dev { | |||
74 | wait_queue_head_t wait; | 74 | wait_queue_head_t wait; |
75 | struct tasklet_struct wakeup_task; | 75 | struct tasklet_struct wakeup_task; |
76 | 76 | ||
77 | struct device *tty_dev; | ||
78 | |||
77 | atomic_t wmem_alloc; | 79 | atomic_t wmem_alloc; |
78 | }; | 80 | }; |
79 | 81 | ||
@@ -261,7 +263,7 @@ out: | |||
261 | return err; | 263 | return err; |
262 | } | 264 | } |
263 | 265 | ||
264 | tty_register_device(rfcomm_tty_driver, dev->id, rfcomm_get_device(dev)); | 266 | dev->tty_dev = tty_register_device(rfcomm_tty_driver, dev->id, NULL); |
265 | 267 | ||
266 | return dev->id; | 268 | return dev->id; |
267 | } | 269 | } |
@@ -630,6 +632,9 @@ static int rfcomm_tty_open(struct tty_struct *tty, struct file *filp) | |||
630 | set_current_state(TASK_RUNNING); | 632 | set_current_state(TASK_RUNNING); |
631 | remove_wait_queue(&dev->wait, &wait); | 633 | remove_wait_queue(&dev->wait, &wait); |
632 | 634 | ||
635 | if (err == 0) | ||
636 | device_move(dev->tty_dev, rfcomm_get_device(dev)); | ||
637 | |||
633 | return err; | 638 | return err; |
634 | } | 639 | } |
635 | 640 | ||
@@ -642,6 +647,8 @@ static void rfcomm_tty_close(struct tty_struct *tty, struct file *filp) | |||
642 | BT_DBG("tty %p dev %p dlc %p opened %d", tty, dev, dev->dlc, dev->opened); | 647 | BT_DBG("tty %p dev %p dlc %p opened %d", tty, dev, dev->dlc, dev->opened); |
643 | 648 | ||
644 | if (--dev->opened == 0) { | 649 | if (--dev->opened == 0) { |
650 | device_move(dev->tty_dev, NULL); | ||
651 | |||
645 | /* Close DLC and dettach TTY */ | 652 | /* Close DLC and dettach TTY */ |
646 | rfcomm_dlc_close(dev->dlc, 0); | 653 | rfcomm_dlc_close(dev->dlc, 0); |
647 | 654 | ||
diff --git a/net/bridge/br_if.c b/net/bridge/br_if.c index aff6a779c9c8..6845a258408f 100644 --- a/net/bridge/br_if.c +++ b/net/bridge/br_if.c | |||
@@ -77,26 +77,15 @@ static int port_cost(struct net_device *dev) | |||
77 | * Called from work queue to allow for calling functions that | 77 | * Called from work queue to allow for calling functions that |
78 | * might sleep (such as speed check), and to debounce. | 78 | * might sleep (such as speed check), and to debounce. |
79 | */ | 79 | */ |
80 | static void port_carrier_check(struct work_struct *work) | 80 | void br_port_carrier_check(struct net_bridge_port *p) |
81 | { | 81 | { |
82 | struct net_bridge_port *p; | 82 | struct net_device *dev = p->dev; |
83 | struct net_device *dev; | 83 | struct net_bridge *br = p->br; |
84 | struct net_bridge *br; | ||
85 | |||
86 | dev = container_of(work, struct net_bridge_port, | ||
87 | carrier_check.work)->dev; | ||
88 | work_release(work); | ||
89 | |||
90 | rtnl_lock(); | ||
91 | p = dev->br_port; | ||
92 | if (!p) | ||
93 | goto done; | ||
94 | br = p->br; | ||
95 | 84 | ||
96 | if (netif_carrier_ok(dev)) | 85 | if (netif_carrier_ok(dev)) |
97 | p->path_cost = port_cost(dev); | 86 | p->path_cost = port_cost(dev); |
98 | 87 | ||
99 | if (br->dev->flags & IFF_UP) { | 88 | if (netif_running(br->dev)) { |
100 | spin_lock_bh(&br->lock); | 89 | spin_lock_bh(&br->lock); |
101 | if (netif_carrier_ok(dev)) { | 90 | if (netif_carrier_ok(dev)) { |
102 | if (p->state == BR_STATE_DISABLED) | 91 | if (p->state == BR_STATE_DISABLED) |
@@ -107,9 +96,6 @@ static void port_carrier_check(struct work_struct *work) | |||
107 | } | 96 | } |
108 | spin_unlock_bh(&br->lock); | 97 | spin_unlock_bh(&br->lock); |
109 | } | 98 | } |
110 | done: | ||
111 | dev_put(dev); | ||
112 | rtnl_unlock(); | ||
113 | } | 99 | } |
114 | 100 | ||
115 | static void release_nbp(struct kobject *kobj) | 101 | static void release_nbp(struct kobject *kobj) |
@@ -162,9 +148,6 @@ static void del_nbp(struct net_bridge_port *p) | |||
162 | 148 | ||
163 | dev_set_promiscuity(dev, -1); | 149 | dev_set_promiscuity(dev, -1); |
164 | 150 | ||
165 | if (cancel_delayed_work(&p->carrier_check)) | ||
166 | dev_put(dev); | ||
167 | |||
168 | spin_lock_bh(&br->lock); | 151 | spin_lock_bh(&br->lock); |
169 | br_stp_disable_port(p); | 152 | br_stp_disable_port(p); |
170 | spin_unlock_bh(&br->lock); | 153 | spin_unlock_bh(&br->lock); |
@@ -282,7 +265,6 @@ static struct net_bridge_port *new_nbp(struct net_bridge *br, | |||
282 | p->port_no = index; | 265 | p->port_no = index; |
283 | br_init_port(p); | 266 | br_init_port(p); |
284 | p->state = BR_STATE_DISABLED; | 267 | p->state = BR_STATE_DISABLED; |
285 | INIT_DELAYED_WORK_NAR(&p->carrier_check, port_carrier_check); | ||
286 | br_stp_port_timer_init(p); | 268 | br_stp_port_timer_init(p); |
287 | 269 | ||
288 | kobject_init(&p->kobj); | 270 | kobject_init(&p->kobj); |
@@ -446,12 +428,10 @@ int br_add_if(struct net_bridge *br, struct net_device *dev) | |||
446 | spin_lock_bh(&br->lock); | 428 | spin_lock_bh(&br->lock); |
447 | br_stp_recalculate_bridge_id(br); | 429 | br_stp_recalculate_bridge_id(br); |
448 | br_features_recompute(br); | 430 | br_features_recompute(br); |
449 | if (schedule_delayed_work(&p->carrier_check, BR_PORT_DEBOUNCE)) | ||
450 | dev_hold(dev); | ||
451 | |||
452 | spin_unlock_bh(&br->lock); | 431 | spin_unlock_bh(&br->lock); |
453 | 432 | ||
454 | dev_set_mtu(br->dev, br_min_mtu(br)); | 433 | dev_set_mtu(br->dev, br_min_mtu(br)); |
434 | |||
455 | kobject_uevent(&p->kobj, KOBJ_ADD); | 435 | kobject_uevent(&p->kobj, KOBJ_ADD); |
456 | 436 | ||
457 | return 0; | 437 | return 0; |
diff --git a/net/bridge/br_notify.c b/net/bridge/br_notify.c index 3311c4e30829..37357ed2149b 100644 --- a/net/bridge/br_notify.c +++ b/net/bridge/br_notify.c | |||
@@ -42,51 +42,48 @@ static int br_device_event(struct notifier_block *unused, unsigned long event, v | |||
42 | 42 | ||
43 | br = p->br; | 43 | br = p->br; |
44 | 44 | ||
45 | spin_lock_bh(&br->lock); | ||
46 | switch (event) { | 45 | switch (event) { |
47 | case NETDEV_CHANGEMTU: | 46 | case NETDEV_CHANGEMTU: |
48 | dev_set_mtu(br->dev, br_min_mtu(br)); | 47 | dev_set_mtu(br->dev, br_min_mtu(br)); |
49 | break; | 48 | break; |
50 | 49 | ||
51 | case NETDEV_CHANGEADDR: | 50 | case NETDEV_CHANGEADDR: |
51 | spin_lock_bh(&br->lock); | ||
52 | br_fdb_changeaddr(p, dev->dev_addr); | 52 | br_fdb_changeaddr(p, dev->dev_addr); |
53 | br_ifinfo_notify(RTM_NEWLINK, p); | 53 | br_ifinfo_notify(RTM_NEWLINK, p); |
54 | br_stp_recalculate_bridge_id(br); | 54 | br_stp_recalculate_bridge_id(br); |
55 | spin_unlock_bh(&br->lock); | ||
55 | break; | 56 | break; |
56 | 57 | ||
57 | case NETDEV_CHANGE: | 58 | case NETDEV_CHANGE: |
58 | if (br->dev->flags & IFF_UP) | 59 | br_port_carrier_check(p); |
59 | if (schedule_delayed_work(&p->carrier_check, | ||
60 | BR_PORT_DEBOUNCE)) | ||
61 | dev_hold(dev); | ||
62 | break; | 60 | break; |
63 | 61 | ||
64 | case NETDEV_FEAT_CHANGE: | 62 | case NETDEV_FEAT_CHANGE: |
65 | if (br->dev->flags & IFF_UP) | 63 | spin_lock_bh(&br->lock); |
64 | if (netif_running(br->dev)) | ||
66 | br_features_recompute(br); | 65 | br_features_recompute(br); |
67 | 66 | spin_unlock_bh(&br->lock); | |
68 | /* could do recursive feature change notification | ||
69 | * but who would care?? | ||
70 | */ | ||
71 | break; | 67 | break; |
72 | 68 | ||
73 | case NETDEV_DOWN: | 69 | case NETDEV_DOWN: |
70 | spin_lock_bh(&br->lock); | ||
74 | if (br->dev->flags & IFF_UP) | 71 | if (br->dev->flags & IFF_UP) |
75 | br_stp_disable_port(p); | 72 | br_stp_disable_port(p); |
73 | spin_unlock_bh(&br->lock); | ||
76 | break; | 74 | break; |
77 | 75 | ||
78 | case NETDEV_UP: | 76 | case NETDEV_UP: |
77 | spin_lock_bh(&br->lock); | ||
79 | if (netif_carrier_ok(dev) && (br->dev->flags & IFF_UP)) | 78 | if (netif_carrier_ok(dev) && (br->dev->flags & IFF_UP)) |
80 | br_stp_enable_port(p); | 79 | br_stp_enable_port(p); |
80 | spin_unlock_bh(&br->lock); | ||
81 | break; | 81 | break; |
82 | 82 | ||
83 | case NETDEV_UNREGISTER: | 83 | case NETDEV_UNREGISTER: |
84 | spin_unlock_bh(&br->lock); | ||
85 | br_del_if(br, dev); | 84 | br_del_if(br, dev); |
86 | goto done; | 85 | break; |
87 | } | 86 | } |
88 | spin_unlock_bh(&br->lock); | ||
89 | 87 | ||
90 | done: | ||
91 | return NOTIFY_DONE; | 88 | return NOTIFY_DONE; |
92 | } | 89 | } |
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h index 6a0540e0591e..cc3f1c99261a 100644 --- a/net/bridge/br_private.h +++ b/net/bridge/br_private.h | |||
@@ -16,7 +16,6 @@ | |||
16 | #define _BR_PRIVATE_H | 16 | #define _BR_PRIVATE_H |
17 | 17 | ||
18 | #include <linux/netdevice.h> | 18 | #include <linux/netdevice.h> |
19 | #include <linux/miscdevice.h> | ||
20 | #include <linux/if_bridge.h> | 19 | #include <linux/if_bridge.h> |
21 | 20 | ||
22 | #define BR_HASH_BITS 8 | 21 | #define BR_HASH_BITS 8 |
@@ -27,8 +26,6 @@ | |||
27 | #define BR_PORT_BITS 10 | 26 | #define BR_PORT_BITS 10 |
28 | #define BR_MAX_PORTS (1<<BR_PORT_BITS) | 27 | #define BR_MAX_PORTS (1<<BR_PORT_BITS) |
29 | 28 | ||
30 | #define BR_PORT_DEBOUNCE (HZ/10) | ||
31 | |||
32 | #define BR_VERSION "2.2" | 29 | #define BR_VERSION "2.2" |
33 | 30 | ||
34 | typedef struct bridge_id bridge_id; | 31 | typedef struct bridge_id bridge_id; |
@@ -82,7 +79,6 @@ struct net_bridge_port | |||
82 | struct timer_list hold_timer; | 79 | struct timer_list hold_timer; |
83 | struct timer_list message_age_timer; | 80 | struct timer_list message_age_timer; |
84 | struct kobject kobj; | 81 | struct kobject kobj; |
85 | struct delayed_work carrier_check; | ||
86 | struct rcu_head rcu; | 82 | struct rcu_head rcu; |
87 | }; | 83 | }; |
88 | 84 | ||
@@ -173,6 +169,7 @@ extern void br_flood_forward(struct net_bridge *br, | |||
173 | int clone); | 169 | int clone); |
174 | 170 | ||
175 | /* br_if.c */ | 171 | /* br_if.c */ |
172 | extern void br_port_carrier_check(struct net_bridge_port *p); | ||
176 | extern int br_add_bridge(const char *name); | 173 | extern int br_add_bridge(const char *name); |
177 | extern int br_del_bridge(const char *name); | 174 | extern int br_del_bridge(const char *name); |
178 | extern void br_cleanup_bridges(void); | 175 | extern void br_cleanup_bridges(void); |
diff --git a/net/bridge/netfilter/ebtables.c b/net/bridge/netfilter/ebtables.c index 34c49799f9b3..ac9984f98e59 100644 --- a/net/bridge/netfilter/ebtables.c +++ b/net/bridge/netfilter/ebtables.c | |||
@@ -833,8 +833,7 @@ static int translate_table(char *name, struct ebt_table_info *newinfo) | |||
833 | /* this will get free'd in do_replace()/ebt_register_table() | 833 | /* this will get free'd in do_replace()/ebt_register_table() |
834 | if an error occurs */ | 834 | if an error occurs */ |
835 | newinfo->chainstack = | 835 | newinfo->chainstack = |
836 | vmalloc((highest_possible_processor_id()+1) | 836 | vmalloc(nr_cpu_ids * sizeof(*(newinfo->chainstack))); |
837 | * sizeof(*(newinfo->chainstack))); | ||
838 | if (!newinfo->chainstack) | 837 | if (!newinfo->chainstack) |
839 | return -ENOMEM; | 838 | return -ENOMEM; |
840 | for_each_possible_cpu(i) { | 839 | for_each_possible_cpu(i) { |
@@ -947,8 +946,7 @@ static int do_replace(void __user *user, unsigned int len) | |||
947 | if (tmp.num_counters >= INT_MAX / sizeof(struct ebt_counter)) | 946 | if (tmp.num_counters >= INT_MAX / sizeof(struct ebt_counter)) |
948 | return -ENOMEM; | 947 | return -ENOMEM; |
949 | 948 | ||
950 | countersize = COUNTER_OFFSET(tmp.nentries) * | 949 | countersize = COUNTER_OFFSET(tmp.nentries) * nr_cpu_ids; |
951 | (highest_possible_processor_id()+1); | ||
952 | newinfo = vmalloc(sizeof(*newinfo) + countersize); | 950 | newinfo = vmalloc(sizeof(*newinfo) + countersize); |
953 | if (!newinfo) | 951 | if (!newinfo) |
954 | return -ENOMEM; | 952 | return -ENOMEM; |
@@ -1168,8 +1166,7 @@ int ebt_register_table(struct ebt_table *table) | |||
1168 | return -EINVAL; | 1166 | return -EINVAL; |
1169 | } | 1167 | } |
1170 | 1168 | ||
1171 | countersize = COUNTER_OFFSET(repl->nentries) * | 1169 | countersize = COUNTER_OFFSET(repl->nentries) * nr_cpu_ids; |
1172 | (highest_possible_processor_id()+1); | ||
1173 | newinfo = vmalloc(sizeof(*newinfo) + countersize); | 1170 | newinfo = vmalloc(sizeof(*newinfo) + countersize); |
1174 | ret = -ENOMEM; | 1171 | ret = -ENOMEM; |
1175 | if (!newinfo) | 1172 | if (!newinfo) |
diff --git a/net/ipv4/Kconfig b/net/ipv4/Kconfig index 91f3a5cdbcf8..9e8ef509c51d 100644 --- a/net/ipv4/Kconfig +++ b/net/ipv4/Kconfig | |||
@@ -442,7 +442,7 @@ config INET_DIAG | |||
442 | ---help--- | 442 | ---help--- |
443 | Support for INET (TCP, DCCP, etc) socket monitoring interface used by | 443 | Support for INET (TCP, DCCP, etc) socket monitoring interface used by |
444 | native Linux tools such as ss. ss is included in iproute2, currently | 444 | native Linux tools such as ss. ss is included in iproute2, currently |
445 | downloadable at <http://developer.osdl.org/dev/iproute2>. | 445 | downloadable at <http://linux-net.osdl.org/index.php/Iproute2>. |
446 | 446 | ||
447 | If unsure, say Y. | 447 | If unsure, say Y. |
448 | 448 | ||
@@ -550,7 +550,7 @@ config TCP_CONG_SCALABLE | |||
550 | Scalable TCP is a sender-side only change to TCP which uses a | 550 | Scalable TCP is a sender-side only change to TCP which uses a |
551 | MIMD congestion control algorithm which has some nice scaling | 551 | MIMD congestion control algorithm which has some nice scaling |
552 | properties, though is known to have fairness issues. | 552 | properties, though is known to have fairness issues. |
553 | See http://www-lce.eng.cam.ac.uk/~ctk21/scalable/ | 553 | See http://www.deneholme.net/tom/scalable/ |
554 | 554 | ||
555 | config TCP_CONG_LP | 555 | config TCP_CONG_LP |
556 | tristate "TCP Low Priority" | 556 | tristate "TCP Low Priority" |
diff --git a/net/ipv4/devinet.c b/net/ipv4/devinet.c index 8a0ec10a13a7..e10794dc5f64 100644 --- a/net/ipv4/devinet.c +++ b/net/ipv4/devinet.c | |||
@@ -1054,12 +1054,14 @@ static int inetdev_event(struct notifier_block *this, unsigned long event, | |||
1054 | ASSERT_RTNL(); | 1054 | ASSERT_RTNL(); |
1055 | 1055 | ||
1056 | if (!in_dev) { | 1056 | if (!in_dev) { |
1057 | if (event == NETDEV_REGISTER && dev == &loopback_dev) { | 1057 | if (event == NETDEV_REGISTER) { |
1058 | in_dev = inetdev_init(dev); | 1058 | in_dev = inetdev_init(dev); |
1059 | if (!in_dev) | 1059 | if (!in_dev) |
1060 | panic("devinet: Failed to create loopback\n"); | 1060 | panic("devinet: Failed to create loopback\n"); |
1061 | in_dev->cnf.no_xfrm = 1; | 1061 | if (dev == &loopback_dev) { |
1062 | in_dev->cnf.no_policy = 1; | 1062 | in_dev->cnf.no_xfrm = 1; |
1063 | in_dev->cnf.no_policy = 1; | ||
1064 | } | ||
1063 | } | 1065 | } |
1064 | goto out; | 1066 | goto out; |
1065 | } | 1067 | } |
diff --git a/net/ipv4/multipath_random.c b/net/ipv4/multipath_random.c index 57f481498fbb..c312785d14d0 100644 --- a/net/ipv4/multipath_random.c +++ b/net/ipv4/multipath_random.c | |||
@@ -32,6 +32,7 @@ | |||
32 | #include <linux/module.h> | 32 | #include <linux/module.h> |
33 | #include <linux/mroute.h> | 33 | #include <linux/mroute.h> |
34 | #include <linux/init.h> | 34 | #include <linux/init.h> |
35 | #include <linux/random.h> | ||
35 | #include <net/ip.h> | 36 | #include <net/ip.h> |
36 | #include <net/protocol.h> | 37 | #include <net/protocol.h> |
37 | #include <linux/skbuff.h> | 38 | #include <linux/skbuff.h> |
@@ -48,21 +49,6 @@ | |||
48 | 49 | ||
49 | #define MULTIPATH_MAX_CANDIDATES 40 | 50 | #define MULTIPATH_MAX_CANDIDATES 40 |
50 | 51 | ||
51 | /* interface to random number generation */ | ||
52 | static unsigned int RANDOM_SEED = 93186752; | ||
53 | |||
54 | static inline unsigned int random(unsigned int ubound) | ||
55 | { | ||
56 | static unsigned int a = 1588635695, | ||
57 | q = 2, | ||
58 | r = 1117695901; | ||
59 | |||
60 | RANDOM_SEED = a*(RANDOM_SEED % q) - r*(RANDOM_SEED / q); | ||
61 | |||
62 | return RANDOM_SEED % ubound; | ||
63 | } | ||
64 | |||
65 | |||
66 | static void random_select_route(const struct flowi *flp, | 52 | static void random_select_route(const struct flowi *flp, |
67 | struct rtable *first, | 53 | struct rtable *first, |
68 | struct rtable **rp) | 54 | struct rtable **rp) |
@@ -84,7 +70,7 @@ static void random_select_route(const struct flowi *flp, | |||
84 | if (candidate_count > 1) { | 70 | if (candidate_count > 1) { |
85 | unsigned char i = 0; | 71 | unsigned char i = 0; |
86 | unsigned char candidate_no = (unsigned char) | 72 | unsigned char candidate_no = (unsigned char) |
87 | random(candidate_count); | 73 | (random32() % candidate_count); |
88 | 74 | ||
89 | /* find chosen candidate and adjust GC data for all candidates | 75 | /* find chosen candidate and adjust GC data for all candidates |
90 | * to ensure they stay in cache | 76 | * to ensure they stay in cache |
diff --git a/net/ipv4/multipath_wrandom.c b/net/ipv4/multipath_wrandom.c index 2bdbb92b450a..57c503694539 100644 --- a/net/ipv4/multipath_wrandom.c +++ b/net/ipv4/multipath_wrandom.c | |||
@@ -32,6 +32,7 @@ | |||
32 | #include <linux/module.h> | 32 | #include <linux/module.h> |
33 | #include <linux/mroute.h> | 33 | #include <linux/mroute.h> |
34 | #include <linux/init.h> | 34 | #include <linux/init.h> |
35 | #include <linux/random.h> | ||
35 | #include <net/ip.h> | 36 | #include <net/ip.h> |
36 | #include <net/protocol.h> | 37 | #include <net/protocol.h> |
37 | #include <linux/skbuff.h> | 38 | #include <linux/skbuff.h> |
@@ -84,18 +85,6 @@ struct multipath_route { | |||
84 | /* state: primarily weight per route information */ | 85 | /* state: primarily weight per route information */ |
85 | static struct multipath_bucket state[MULTIPATH_STATE_SIZE]; | 86 | static struct multipath_bucket state[MULTIPATH_STATE_SIZE]; |
86 | 87 | ||
87 | /* interface to random number generation */ | ||
88 | static unsigned int RANDOM_SEED = 93186752; | ||
89 | |||
90 | static inline unsigned int random(unsigned int ubound) | ||
91 | { | ||
92 | static unsigned int a = 1588635695, | ||
93 | q = 2, | ||
94 | r = 1117695901; | ||
95 | RANDOM_SEED = a*(RANDOM_SEED % q) - r*(RANDOM_SEED / q); | ||
96 | return RANDOM_SEED % ubound; | ||
97 | } | ||
98 | |||
99 | static unsigned char __multipath_lookup_weight(const struct flowi *fl, | 88 | static unsigned char __multipath_lookup_weight(const struct flowi *fl, |
100 | const struct rtable *rt) | 89 | const struct rtable *rt) |
101 | { | 90 | { |
@@ -193,7 +182,7 @@ static void wrandom_select_route(const struct flowi *flp, | |||
193 | 182 | ||
194 | /* choose a weighted random candidate */ | 183 | /* choose a weighted random candidate */ |
195 | decision = first; | 184 | decision = first; |
196 | selector = random(power); | 185 | selector = random32() % power; |
197 | last_power = 0; | 186 | last_power = 0; |
198 | 187 | ||
199 | /* select candidate, adjust GC data and cleanup local state */ | 188 | /* select candidate, adjust GC data and cleanup local state */ |
diff --git a/net/ipv4/tcp.c b/net/ipv4/tcp.c index ac6516c642a1..74c4d103ebc2 100644 --- a/net/ipv4/tcp.c +++ b/net/ipv4/tcp.c | |||
@@ -2266,12 +2266,12 @@ void tcp_free_md5sig_pool(void) | |||
2266 | { | 2266 | { |
2267 | struct tcp_md5sig_pool **pool = NULL; | 2267 | struct tcp_md5sig_pool **pool = NULL; |
2268 | 2268 | ||
2269 | spin_lock(&tcp_md5sig_pool_lock); | 2269 | spin_lock_bh(&tcp_md5sig_pool_lock); |
2270 | if (--tcp_md5sig_users == 0) { | 2270 | if (--tcp_md5sig_users == 0) { |
2271 | pool = tcp_md5sig_pool; | 2271 | pool = tcp_md5sig_pool; |
2272 | tcp_md5sig_pool = NULL; | 2272 | tcp_md5sig_pool = NULL; |
2273 | } | 2273 | } |
2274 | spin_unlock(&tcp_md5sig_pool_lock); | 2274 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2275 | if (pool) | 2275 | if (pool) |
2276 | __tcp_free_md5sig_pool(pool); | 2276 | __tcp_free_md5sig_pool(pool); |
2277 | } | 2277 | } |
@@ -2314,36 +2314,36 @@ struct tcp_md5sig_pool **tcp_alloc_md5sig_pool(void) | |||
2314 | int alloc = 0; | 2314 | int alloc = 0; |
2315 | 2315 | ||
2316 | retry: | 2316 | retry: |
2317 | spin_lock(&tcp_md5sig_pool_lock); | 2317 | spin_lock_bh(&tcp_md5sig_pool_lock); |
2318 | pool = tcp_md5sig_pool; | 2318 | pool = tcp_md5sig_pool; |
2319 | if (tcp_md5sig_users++ == 0) { | 2319 | if (tcp_md5sig_users++ == 0) { |
2320 | alloc = 1; | 2320 | alloc = 1; |
2321 | spin_unlock(&tcp_md5sig_pool_lock); | 2321 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2322 | } else if (!pool) { | 2322 | } else if (!pool) { |
2323 | tcp_md5sig_users--; | 2323 | tcp_md5sig_users--; |
2324 | spin_unlock(&tcp_md5sig_pool_lock); | 2324 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2325 | cpu_relax(); | 2325 | cpu_relax(); |
2326 | goto retry; | 2326 | goto retry; |
2327 | } else | 2327 | } else |
2328 | spin_unlock(&tcp_md5sig_pool_lock); | 2328 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2329 | 2329 | ||
2330 | if (alloc) { | 2330 | if (alloc) { |
2331 | /* we cannot hold spinlock here because this may sleep. */ | 2331 | /* we cannot hold spinlock here because this may sleep. */ |
2332 | struct tcp_md5sig_pool **p = __tcp_alloc_md5sig_pool(); | 2332 | struct tcp_md5sig_pool **p = __tcp_alloc_md5sig_pool(); |
2333 | spin_lock(&tcp_md5sig_pool_lock); | 2333 | spin_lock_bh(&tcp_md5sig_pool_lock); |
2334 | if (!p) { | 2334 | if (!p) { |
2335 | tcp_md5sig_users--; | 2335 | tcp_md5sig_users--; |
2336 | spin_unlock(&tcp_md5sig_pool_lock); | 2336 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2337 | return NULL; | 2337 | return NULL; |
2338 | } | 2338 | } |
2339 | pool = tcp_md5sig_pool; | 2339 | pool = tcp_md5sig_pool; |
2340 | if (pool) { | 2340 | if (pool) { |
2341 | /* oops, it has already been assigned. */ | 2341 | /* oops, it has already been assigned. */ |
2342 | spin_unlock(&tcp_md5sig_pool_lock); | 2342 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2343 | __tcp_free_md5sig_pool(p); | 2343 | __tcp_free_md5sig_pool(p); |
2344 | } else { | 2344 | } else { |
2345 | tcp_md5sig_pool = pool = p; | 2345 | tcp_md5sig_pool = pool = p; |
2346 | spin_unlock(&tcp_md5sig_pool_lock); | 2346 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2347 | } | 2347 | } |
2348 | } | 2348 | } |
2349 | return pool; | 2349 | return pool; |
@@ -2354,11 +2354,11 @@ EXPORT_SYMBOL(tcp_alloc_md5sig_pool); | |||
2354 | struct tcp_md5sig_pool *__tcp_get_md5sig_pool(int cpu) | 2354 | struct tcp_md5sig_pool *__tcp_get_md5sig_pool(int cpu) |
2355 | { | 2355 | { |
2356 | struct tcp_md5sig_pool **p; | 2356 | struct tcp_md5sig_pool **p; |
2357 | spin_lock(&tcp_md5sig_pool_lock); | 2357 | spin_lock_bh(&tcp_md5sig_pool_lock); |
2358 | p = tcp_md5sig_pool; | 2358 | p = tcp_md5sig_pool; |
2359 | if (p) | 2359 | if (p) |
2360 | tcp_md5sig_users++; | 2360 | tcp_md5sig_users++; |
2361 | spin_unlock(&tcp_md5sig_pool_lock); | 2361 | spin_unlock_bh(&tcp_md5sig_pool_lock); |
2362 | return (p ? *per_cpu_ptr(p, cpu) : NULL); | 2362 | return (p ? *per_cpu_ptr(p, cpu) : NULL); |
2363 | } | 2363 | } |
2364 | 2364 | ||
diff --git a/net/ipv4/xfrm4_mode_tunnel.c b/net/ipv4/xfrm4_mode_tunnel.c index e1cab33fdad1..ceb4376f572a 100644 --- a/net/ipv4/xfrm4_mode_tunnel.c +++ b/net/ipv4/xfrm4_mode_tunnel.c | |||
@@ -111,6 +111,7 @@ static int xfrm4_tunnel_input(struct xfrm_state *x, struct sk_buff *skb) | |||
111 | (err = pskb_expand_head(skb, 0, 0, GFP_ATOMIC))) | 111 | (err = pskb_expand_head(skb, 0, 0, GFP_ATOMIC))) |
112 | goto out; | 112 | goto out; |
113 | 113 | ||
114 | iph = skb->nh.iph; | ||
114 | if (iph->protocol == IPPROTO_IPIP) { | 115 | if (iph->protocol == IPPROTO_IPIP) { |
115 | if (x->props.flags & XFRM_STATE_DECAP_DSCP) | 116 | if (x->props.flags & XFRM_STATE_DECAP_DSCP) |
116 | ipv4_copy_dscp(iph, skb->h.ipiph); | 117 | ipv4_copy_dscp(iph, skb->h.ipiph); |
diff --git a/net/ipv4/xfrm4_policy.c b/net/ipv4/xfrm4_policy.c index fef19c6bcb98..5d51a2af34c1 100644 --- a/net/ipv4/xfrm4_policy.c +++ b/net/ipv4/xfrm4_policy.c | |||
@@ -291,7 +291,7 @@ static void xfrm4_dst_destroy(struct dst_entry *dst) | |||
291 | 291 | ||
292 | if (likely(xdst->u.rt.idev)) | 292 | if (likely(xdst->u.rt.idev)) |
293 | in_dev_put(xdst->u.rt.idev); | 293 | in_dev_put(xdst->u.rt.idev); |
294 | if (dst->xfrm->props.family == AF_INET && likely(xdst->u.rt.peer)) | 294 | if (dst->xfrm && dst->xfrm->props.family == AF_INET && likely(xdst->u.rt.peer)) |
295 | inet_putpeer(xdst->u.rt.peer); | 295 | inet_putpeer(xdst->u.rt.peer); |
296 | xfrm_dst_destroy(xdst); | 296 | xfrm_dst_destroy(xdst); |
297 | } | 297 | } |
diff --git a/net/ipv6/Makefile b/net/ipv6/Makefile index 8bacda109b7f..d460017bb353 100644 --- a/net/ipv6/Makefile +++ b/net/ipv6/Makefile | |||
@@ -32,6 +32,6 @@ obj-$(CONFIG_NETFILTER) += netfilter/ | |||
32 | obj-$(CONFIG_IPV6_SIT) += sit.o | 32 | obj-$(CONFIG_IPV6_SIT) += sit.o |
33 | obj-$(CONFIG_IPV6_TUNNEL) += ip6_tunnel.o | 33 | obj-$(CONFIG_IPV6_TUNNEL) += ip6_tunnel.o |
34 | 34 | ||
35 | obj-y += exthdrs_core.o | 35 | obj-y += addrconf_core.o exthdrs_core.o |
36 | 36 | ||
37 | obj-$(subst m,y,$(CONFIG_IPV6)) += inet6_hashtables.o | 37 | obj-$(subst m,y,$(CONFIG_IPV6)) += inet6_hashtables.o |
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c index 569a37d698f7..f6ac65d36559 100644 --- a/net/ipv6/addrconf.c +++ b/net/ipv6/addrconf.c | |||
@@ -211,74 +211,6 @@ const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT; | |||
211 | #endif | 211 | #endif |
212 | const struct in6_addr in6addr_loopback = IN6ADDR_LOOPBACK_INIT; | 212 | const struct in6_addr in6addr_loopback = IN6ADDR_LOOPBACK_INIT; |
213 | 213 | ||
214 | #define IPV6_ADDR_SCOPE_TYPE(scope) ((scope) << 16) | ||
215 | |||
216 | static inline unsigned ipv6_addr_scope2type(unsigned scope) | ||
217 | { | ||
218 | switch(scope) { | ||
219 | case IPV6_ADDR_SCOPE_NODELOCAL: | ||
220 | return (IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_NODELOCAL) | | ||
221 | IPV6_ADDR_LOOPBACK); | ||
222 | case IPV6_ADDR_SCOPE_LINKLOCAL: | ||
223 | return (IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_LINKLOCAL) | | ||
224 | IPV6_ADDR_LINKLOCAL); | ||
225 | case IPV6_ADDR_SCOPE_SITELOCAL: | ||
226 | return (IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_SITELOCAL) | | ||
227 | IPV6_ADDR_SITELOCAL); | ||
228 | } | ||
229 | return IPV6_ADDR_SCOPE_TYPE(scope); | ||
230 | } | ||
231 | |||
232 | int __ipv6_addr_type(const struct in6_addr *addr) | ||
233 | { | ||
234 | __be32 st; | ||
235 | |||
236 | st = addr->s6_addr32[0]; | ||
237 | |||
238 | /* Consider all addresses with the first three bits different of | ||
239 | 000 and 111 as unicasts. | ||
240 | */ | ||
241 | if ((st & htonl(0xE0000000)) != htonl(0x00000000) && | ||
242 | (st & htonl(0xE0000000)) != htonl(0xE0000000)) | ||
243 | return (IPV6_ADDR_UNICAST | | ||
244 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); | ||
245 | |||
246 | if ((st & htonl(0xFF000000)) == htonl(0xFF000000)) { | ||
247 | /* multicast */ | ||
248 | /* addr-select 3.1 */ | ||
249 | return (IPV6_ADDR_MULTICAST | | ||
250 | ipv6_addr_scope2type(IPV6_ADDR_MC_SCOPE(addr))); | ||
251 | } | ||
252 | |||
253 | if ((st & htonl(0xFFC00000)) == htonl(0xFE800000)) | ||
254 | return (IPV6_ADDR_LINKLOCAL | IPV6_ADDR_UNICAST | | ||
255 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_LINKLOCAL)); /* addr-select 3.1 */ | ||
256 | if ((st & htonl(0xFFC00000)) == htonl(0xFEC00000)) | ||
257 | return (IPV6_ADDR_SITELOCAL | IPV6_ADDR_UNICAST | | ||
258 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_SITELOCAL)); /* addr-select 3.1 */ | ||
259 | |||
260 | if ((addr->s6_addr32[0] | addr->s6_addr32[1]) == 0) { | ||
261 | if (addr->s6_addr32[2] == 0) { | ||
262 | if (addr->s6_addr32[3] == 0) | ||
263 | return IPV6_ADDR_ANY; | ||
264 | |||
265 | if (addr->s6_addr32[3] == htonl(0x00000001)) | ||
266 | return (IPV6_ADDR_LOOPBACK | IPV6_ADDR_UNICAST | | ||
267 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_LINKLOCAL)); /* addr-select 3.4 */ | ||
268 | |||
269 | return (IPV6_ADDR_COMPATv4 | IPV6_ADDR_UNICAST | | ||
270 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); /* addr-select 3.3 */ | ||
271 | } | ||
272 | |||
273 | if (addr->s6_addr32[2] == htonl(0x0000ffff)) | ||
274 | return (IPV6_ADDR_MAPPED | | ||
275 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); /* addr-select 3.3 */ | ||
276 | } | ||
277 | |||
278 | return (IPV6_ADDR_RESERVED | | ||
279 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); /* addr-select 3.4 */ | ||
280 | } | ||
281 | |||
282 | static void addrconf_del_timer(struct inet6_ifaddr *ifp) | 214 | static void addrconf_del_timer(struct inet6_ifaddr *ifp) |
283 | { | 215 | { |
284 | if (del_timer(&ifp->timer)) | 216 | if (del_timer(&ifp->timer)) |
@@ -1910,6 +1842,7 @@ static int inet6_addr_add(int ifindex, struct in6_addr *pfx, int plen, | |||
1910 | struct inet6_dev *idev; | 1842 | struct inet6_dev *idev; |
1911 | struct net_device *dev; | 1843 | struct net_device *dev; |
1912 | int scope; | 1844 | int scope; |
1845 | u32 flags = RTF_EXPIRES; | ||
1913 | 1846 | ||
1914 | ASSERT_RTNL(); | 1847 | ASSERT_RTNL(); |
1915 | 1848 | ||
@@ -1925,9 +1858,10 @@ static int inet6_addr_add(int ifindex, struct in6_addr *pfx, int plen, | |||
1925 | 1858 | ||
1926 | scope = ipv6_addr_scope(pfx); | 1859 | scope = ipv6_addr_scope(pfx); |
1927 | 1860 | ||
1928 | if (valid_lft == INFINITY_LIFE_TIME) | 1861 | if (valid_lft == INFINITY_LIFE_TIME) { |
1929 | ifa_flags |= IFA_F_PERMANENT; | 1862 | ifa_flags |= IFA_F_PERMANENT; |
1930 | else if (valid_lft >= 0x7FFFFFFF/HZ) | 1863 | flags = 0; |
1864 | } else if (valid_lft >= 0x7FFFFFFF/HZ) | ||
1931 | valid_lft = 0x7FFFFFFF/HZ; | 1865 | valid_lft = 0x7FFFFFFF/HZ; |
1932 | 1866 | ||
1933 | if (prefered_lft == 0) | 1867 | if (prefered_lft == 0) |
@@ -1945,6 +1879,8 @@ static int inet6_addr_add(int ifindex, struct in6_addr *pfx, int plen, | |||
1945 | ifp->tstamp = jiffies; | 1879 | ifp->tstamp = jiffies; |
1946 | spin_unlock_bh(&ifp->lock); | 1880 | spin_unlock_bh(&ifp->lock); |
1947 | 1881 | ||
1882 | addrconf_prefix_route(&ifp->addr, ifp->prefix_len, dev, | ||
1883 | jiffies_to_clock_t(valid_lft * HZ), flags); | ||
1948 | addrconf_dad_start(ifp, 0); | 1884 | addrconf_dad_start(ifp, 0); |
1949 | in6_ifa_put(ifp); | 1885 | in6_ifa_put(ifp); |
1950 | addrconf_verify(0); | 1886 | addrconf_verify(0); |
@@ -2124,6 +2060,7 @@ static void addrconf_add_linklocal(struct inet6_dev *idev, struct in6_addr *addr | |||
2124 | 2060 | ||
2125 | ifp = ipv6_add_addr(idev, addr, 64, IFA_LINK, IFA_F_PERMANENT); | 2061 | ifp = ipv6_add_addr(idev, addr, 64, IFA_LINK, IFA_F_PERMANENT); |
2126 | if (!IS_ERR(ifp)) { | 2062 | if (!IS_ERR(ifp)) { |
2063 | addrconf_prefix_route(&ifp->addr, ifp->prefix_len, idev->dev, 0, 0); | ||
2127 | addrconf_dad_start(ifp, 0); | 2064 | addrconf_dad_start(ifp, 0); |
2128 | in6_ifa_put(ifp); | 2065 | in6_ifa_put(ifp); |
2129 | } | 2066 | } |
@@ -2240,6 +2177,14 @@ static int addrconf_notify(struct notifier_block *this, unsigned long event, | |||
2240 | int run_pending = 0; | 2177 | int run_pending = 0; |
2241 | 2178 | ||
2242 | switch(event) { | 2179 | switch(event) { |
2180 | case NETDEV_REGISTER: | ||
2181 | if (!idev) { | ||
2182 | idev = ipv6_add_dev(dev); | ||
2183 | if (!idev) | ||
2184 | printk(KERN_WARNING "IPv6: add_dev failed for %s\n", | ||
2185 | dev->name); | ||
2186 | } | ||
2187 | break; | ||
2243 | case NETDEV_UP: | 2188 | case NETDEV_UP: |
2244 | case NETDEV_CHANGE: | 2189 | case NETDEV_CHANGE: |
2245 | if (event == NETDEV_UP) { | 2190 | if (event == NETDEV_UP) { |
@@ -2538,10 +2483,6 @@ static void addrconf_dad_start(struct inet6_ifaddr *ifp, u32 flags) | |||
2538 | 2483 | ||
2539 | addrconf_join_solict(dev, &ifp->addr); | 2484 | addrconf_join_solict(dev, &ifp->addr); |
2540 | 2485 | ||
2541 | if (ifp->prefix_len != 128 && (ifp->flags&IFA_F_PERMANENT)) | ||
2542 | addrconf_prefix_route(&ifp->addr, ifp->prefix_len, dev, 0, | ||
2543 | flags); | ||
2544 | |||
2545 | net_srandom(ifp->addr.s6_addr32[3]); | 2486 | net_srandom(ifp->addr.s6_addr32[3]); |
2546 | 2487 | ||
2547 | read_lock_bh(&idev->lock); | 2488 | read_lock_bh(&idev->lock); |
@@ -2972,12 +2913,15 @@ inet6_rtm_deladdr(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg) | |||
2972 | static int inet6_addr_modify(struct inet6_ifaddr *ifp, u8 ifa_flags, | 2913 | static int inet6_addr_modify(struct inet6_ifaddr *ifp, u8 ifa_flags, |
2973 | u32 prefered_lft, u32 valid_lft) | 2914 | u32 prefered_lft, u32 valid_lft) |
2974 | { | 2915 | { |
2916 | u32 flags = RTF_EXPIRES; | ||
2917 | |||
2975 | if (!valid_lft || (prefered_lft > valid_lft)) | 2918 | if (!valid_lft || (prefered_lft > valid_lft)) |
2976 | return -EINVAL; | 2919 | return -EINVAL; |
2977 | 2920 | ||
2978 | if (valid_lft == INFINITY_LIFE_TIME) | 2921 | if (valid_lft == INFINITY_LIFE_TIME) { |
2979 | ifa_flags |= IFA_F_PERMANENT; | 2922 | ifa_flags |= IFA_F_PERMANENT; |
2980 | else if (valid_lft >= 0x7FFFFFFF/HZ) | 2923 | flags = 0; |
2924 | } else if (valid_lft >= 0x7FFFFFFF/HZ) | ||
2981 | valid_lft = 0x7FFFFFFF/HZ; | 2925 | valid_lft = 0x7FFFFFFF/HZ; |
2982 | 2926 | ||
2983 | if (prefered_lft == 0) | 2927 | if (prefered_lft == 0) |
@@ -2996,6 +2940,8 @@ static int inet6_addr_modify(struct inet6_ifaddr *ifp, u8 ifa_flags, | |||
2996 | if (!(ifp->flags&IFA_F_TENTATIVE)) | 2940 | if (!(ifp->flags&IFA_F_TENTATIVE)) |
2997 | ipv6_ifa_notify(0, ifp); | 2941 | ipv6_ifa_notify(0, ifp); |
2998 | 2942 | ||
2943 | addrconf_prefix_route(&ifp->addr, ifp->prefix_len, ifp->idev->dev, | ||
2944 | jiffies_to_clock_t(valid_lft * HZ), flags); | ||
2999 | addrconf_verify(0); | 2945 | addrconf_verify(0); |
3000 | 2946 | ||
3001 | return 0; | 2947 | return 0; |
diff --git a/net/ipv6/addrconf_core.c b/net/ipv6/addrconf_core.c new file mode 100644 index 000000000000..faaefb692298 --- /dev/null +++ b/net/ipv6/addrconf_core.c | |||
@@ -0,0 +1,76 @@ | |||
1 | /* | ||
2 | * IPv6 library code, needed by static components when full IPv6 support is | ||
3 | * not configured or static. | ||
4 | */ | ||
5 | |||
6 | #include <net/ipv6.h> | ||
7 | |||
8 | #define IPV6_ADDR_SCOPE_TYPE(scope) ((scope) << 16) | ||
9 | |||
10 | static inline unsigned ipv6_addr_scope2type(unsigned scope) | ||
11 | { | ||
12 | switch(scope) { | ||
13 | case IPV6_ADDR_SCOPE_NODELOCAL: | ||
14 | return (IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_NODELOCAL) | | ||
15 | IPV6_ADDR_LOOPBACK); | ||
16 | case IPV6_ADDR_SCOPE_LINKLOCAL: | ||
17 | return (IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_LINKLOCAL) | | ||
18 | IPV6_ADDR_LINKLOCAL); | ||
19 | case IPV6_ADDR_SCOPE_SITELOCAL: | ||
20 | return (IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_SITELOCAL) | | ||
21 | IPV6_ADDR_SITELOCAL); | ||
22 | } | ||
23 | return IPV6_ADDR_SCOPE_TYPE(scope); | ||
24 | } | ||
25 | |||
26 | int __ipv6_addr_type(const struct in6_addr *addr) | ||
27 | { | ||
28 | __be32 st; | ||
29 | |||
30 | st = addr->s6_addr32[0]; | ||
31 | |||
32 | /* Consider all addresses with the first three bits different of | ||
33 | 000 and 111 as unicasts. | ||
34 | */ | ||
35 | if ((st & htonl(0xE0000000)) != htonl(0x00000000) && | ||
36 | (st & htonl(0xE0000000)) != htonl(0xE0000000)) | ||
37 | return (IPV6_ADDR_UNICAST | | ||
38 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); | ||
39 | |||
40 | if ((st & htonl(0xFF000000)) == htonl(0xFF000000)) { | ||
41 | /* multicast */ | ||
42 | /* addr-select 3.1 */ | ||
43 | return (IPV6_ADDR_MULTICAST | | ||
44 | ipv6_addr_scope2type(IPV6_ADDR_MC_SCOPE(addr))); | ||
45 | } | ||
46 | |||
47 | if ((st & htonl(0xFFC00000)) == htonl(0xFE800000)) | ||
48 | return (IPV6_ADDR_LINKLOCAL | IPV6_ADDR_UNICAST | | ||
49 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_LINKLOCAL)); /* addr-select 3.1 */ | ||
50 | if ((st & htonl(0xFFC00000)) == htonl(0xFEC00000)) | ||
51 | return (IPV6_ADDR_SITELOCAL | IPV6_ADDR_UNICAST | | ||
52 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_SITELOCAL)); /* addr-select 3.1 */ | ||
53 | |||
54 | if ((addr->s6_addr32[0] | addr->s6_addr32[1]) == 0) { | ||
55 | if (addr->s6_addr32[2] == 0) { | ||
56 | if (addr->s6_addr32[3] == 0) | ||
57 | return IPV6_ADDR_ANY; | ||
58 | |||
59 | if (addr->s6_addr32[3] == htonl(0x00000001)) | ||
60 | return (IPV6_ADDR_LOOPBACK | IPV6_ADDR_UNICAST | | ||
61 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_LINKLOCAL)); /* addr-select 3.4 */ | ||
62 | |||
63 | return (IPV6_ADDR_COMPATv4 | IPV6_ADDR_UNICAST | | ||
64 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); /* addr-select 3.3 */ | ||
65 | } | ||
66 | |||
67 | if (addr->s6_addr32[2] == htonl(0x0000ffff)) | ||
68 | return (IPV6_ADDR_MAPPED | | ||
69 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); /* addr-select 3.3 */ | ||
70 | } | ||
71 | |||
72 | return (IPV6_ADDR_RESERVED | | ||
73 | IPV6_ADDR_SCOPE_TYPE(IPV6_ADDR_SCOPE_GLOBAL)); /* addr-select 3.4 */ | ||
74 | } | ||
75 | EXPORT_SYMBOL(__ipv6_addr_type); | ||
76 | |||
diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c index 3585d8fa7f02..5cac14a5c778 100644 --- a/net/ipv6/af_inet6.c +++ b/net/ipv6/af_inet6.c | |||
@@ -929,25 +929,28 @@ static void __exit inet6_exit(void) | |||
929 | { | 929 | { |
930 | /* First of all disallow new sockets creation. */ | 930 | /* First of all disallow new sockets creation. */ |
931 | sock_unregister(PF_INET6); | 931 | sock_unregister(PF_INET6); |
932 | |||
933 | /* Cleanup code parts. */ | ||
934 | ipv6_packet_cleanup(); | ||
935 | #ifdef CONFIG_IPV6_MIP6 | ||
936 | mip6_fini(); | ||
937 | #endif | ||
938 | addrconf_cleanup(); | ||
939 | ip6_flowlabel_cleanup(); | ||
940 | ip6_route_cleanup(); | ||
932 | #ifdef CONFIG_PROC_FS | 941 | #ifdef CONFIG_PROC_FS |
942 | |||
943 | /* Cleanup code parts. */ | ||
933 | if6_proc_exit(); | 944 | if6_proc_exit(); |
934 | ac6_proc_exit(); | 945 | ac6_proc_exit(); |
935 | ipv6_misc_proc_exit(); | 946 | ipv6_misc_proc_exit(); |
936 | udp6_proc_exit(); | ||
937 | udplite6_proc_exit(); | 947 | udplite6_proc_exit(); |
948 | udp6_proc_exit(); | ||
938 | tcp6_proc_exit(); | 949 | tcp6_proc_exit(); |
939 | raw6_proc_exit(); | 950 | raw6_proc_exit(); |
940 | #endif | 951 | #endif |
941 | #ifdef CONFIG_IPV6_MIP6 | ||
942 | mip6_fini(); | ||
943 | #endif | ||
944 | /* Cleanup code parts. */ | ||
945 | ip6_flowlabel_cleanup(); | ||
946 | addrconf_cleanup(); | ||
947 | ip6_route_cleanup(); | ||
948 | ipv6_packet_cleanup(); | ||
949 | igmp6_cleanup(); | ||
950 | ipv6_netfilter_fini(); | 952 | ipv6_netfilter_fini(); |
953 | igmp6_cleanup(); | ||
951 | ndisc_cleanup(); | 954 | ndisc_cleanup(); |
952 | icmpv6_cleanup(); | 955 | icmpv6_cleanup(); |
953 | #ifdef CONFIG_SYSCTL | 956 | #ifdef CONFIG_SYSCTL |
@@ -955,6 +958,7 @@ static void __exit inet6_exit(void) | |||
955 | #endif | 958 | #endif |
956 | cleanup_ipv6_mibs(); | 959 | cleanup_ipv6_mibs(); |
957 | proto_unregister(&rawv6_prot); | 960 | proto_unregister(&rawv6_prot); |
961 | proto_unregister(&udplitev6_prot); | ||
958 | proto_unregister(&udpv6_prot); | 962 | proto_unregister(&udpv6_prot); |
959 | proto_unregister(&tcpv6_prot); | 963 | proto_unregister(&tcpv6_prot); |
960 | } | 964 | } |
diff --git a/net/ipv6/ip6_tunnel.c b/net/ipv6/ip6_tunnel.c index 662edb826899..08d944223ec8 100644 --- a/net/ipv6/ip6_tunnel.c +++ b/net/ipv6/ip6_tunnel.c | |||
@@ -727,11 +727,8 @@ ip6ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev) | |||
727 | } | 727 | } |
728 | if (mtu < IPV6_MIN_MTU) | 728 | if (mtu < IPV6_MIN_MTU) |
729 | mtu = IPV6_MIN_MTU; | 729 | mtu = IPV6_MIN_MTU; |
730 | if (skb->dst && mtu < dst_mtu(skb->dst)) { | 730 | if (skb->dst) |
731 | struct rt6_info *rt = (struct rt6_info *) skb->dst; | 731 | skb->dst->ops->update_pmtu(skb->dst, mtu); |
732 | rt->rt6i_flags |= RTF_MODIFIED; | ||
733 | rt->u.dst.metrics[RTAX_MTU-1] = mtu; | ||
734 | } | ||
735 | if (skb->len > mtu) { | 732 | if (skb->len > mtu) { |
736 | icmpv6_send(skb, ICMPV6_PKT_TOOBIG, 0, mtu, dev); | 733 | icmpv6_send(skb, ICMPV6_PKT_TOOBIG, 0, mtu, dev); |
737 | goto tx_err_dst_release; | 734 | goto tx_err_dst_release; |
diff --git a/net/ipv6/ipv6_syms.c b/net/ipv6/ipv6_syms.c index 0e8e0676a033..e12e3d4fccec 100644 --- a/net/ipv6/ipv6_syms.c +++ b/net/ipv6/ipv6_syms.c | |||
@@ -6,7 +6,6 @@ | |||
6 | #include <net/ip6_route.h> | 6 | #include <net/ip6_route.h> |
7 | #include <net/xfrm.h> | 7 | #include <net/xfrm.h> |
8 | 8 | ||
9 | EXPORT_SYMBOL(__ipv6_addr_type); | ||
10 | EXPORT_SYMBOL(icmpv6_send); | 9 | EXPORT_SYMBOL(icmpv6_send); |
11 | EXPORT_SYMBOL(icmpv6_statistics); | 10 | EXPORT_SYMBOL(icmpv6_statistics); |
12 | EXPORT_SYMBOL(icmpv6_err_convert); | 11 | EXPORT_SYMBOL(icmpv6_err_convert); |
diff --git a/net/ipv6/xfrm6_policy.c b/net/ipv6/xfrm6_policy.c index b1133f27c8ae..d8a585bd2cb4 100644 --- a/net/ipv6/xfrm6_policy.c +++ b/net/ipv6/xfrm6_policy.c | |||
@@ -189,7 +189,7 @@ __xfrm6_bundle_create(struct xfrm_policy *policy, struct xfrm_state **xfrm, int | |||
189 | case AF_INET6: | 189 | case AF_INET6: |
190 | ipv6_addr_copy(&fl_tunnel.fl6_dst, __xfrm6_bundle_addr_remote(xfrm[i], &fl->fl6_dst)); | 190 | ipv6_addr_copy(&fl_tunnel.fl6_dst, __xfrm6_bundle_addr_remote(xfrm[i], &fl->fl6_dst)); |
191 | 191 | ||
192 | ipv6_addr_copy(&fl_tunnel.fl6_src, __xfrm6_bundle_addr_remote(xfrm[i], &fl->fl6_src)); | 192 | ipv6_addr_copy(&fl_tunnel.fl6_src, __xfrm6_bundle_addr_local(xfrm[i], &fl->fl6_src)); |
193 | break; | 193 | break; |
194 | default: | 194 | default: |
195 | BUG_ON(1); | 195 | BUG_ON(1); |
diff --git a/net/irda/irmod.c b/net/irda/irmod.c index 826e6c4ca5d5..c7fad2c5b9f3 100644 --- a/net/irda/irmod.c +++ b/net/irda/irmod.c | |||
@@ -42,19 +42,6 @@ | |||
42 | #include <net/irda/irttp.h> /* irttp_init */ | 42 | #include <net/irda/irttp.h> /* irttp_init */ |
43 | #include <net/irda/irda_device.h> /* irda_device_init */ | 43 | #include <net/irda/irda_device.h> /* irda_device_init */ |
44 | 44 | ||
45 | /* irproc.c */ | ||
46 | extern void irda_proc_register(void); | ||
47 | extern void irda_proc_unregister(void); | ||
48 | /* irsysctl.c */ | ||
49 | extern int irda_sysctl_register(void); | ||
50 | extern void irda_sysctl_unregister(void); | ||
51 | /* af_irda.c */ | ||
52 | extern int irsock_init(void); | ||
53 | extern void irsock_cleanup(void); | ||
54 | /* irlap_frame.c */ | ||
55 | extern int irlap_driver_rcv(struct sk_buff *, struct net_device *, | ||
56 | struct packet_type *, struct net_device *); | ||
57 | |||
58 | /* | 45 | /* |
59 | * Module parameters | 46 | * Module parameters |
60 | */ | 47 | */ |
diff --git a/net/packet/af_packet.c b/net/packet/af_packet.c index bf2699074774..28d47e8f2873 100644 --- a/net/packet/af_packet.c +++ b/net/packet/af_packet.c | |||
@@ -227,17 +227,14 @@ struct packet_skb_cb { | |||
227 | 227 | ||
228 | #ifdef CONFIG_PACKET_MMAP | 228 | #ifdef CONFIG_PACKET_MMAP |
229 | 229 | ||
230 | static inline char *packet_lookup_frame(struct packet_sock *po, unsigned int position) | 230 | static inline struct tpacket_hdr *packet_lookup_frame(struct packet_sock *po, unsigned int position) |
231 | { | 231 | { |
232 | unsigned int pg_vec_pos, frame_offset; | 232 | unsigned int pg_vec_pos, frame_offset; |
233 | char *frame; | ||
234 | 233 | ||
235 | pg_vec_pos = position / po->frames_per_block; | 234 | pg_vec_pos = position / po->frames_per_block; |
236 | frame_offset = position % po->frames_per_block; | 235 | frame_offset = position % po->frames_per_block; |
237 | 236 | ||
238 | frame = po->pg_vec[pg_vec_pos] + (frame_offset * po->frame_size); | 237 | return (struct tpacket_hdr *)(po->pg_vec[pg_vec_pos] + (frame_offset * po->frame_size)); |
239 | |||
240 | return frame; | ||
241 | } | 238 | } |
242 | #endif | 239 | #endif |
243 | 240 | ||
@@ -639,7 +636,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev, struct packe | |||
639 | } | 636 | } |
640 | 637 | ||
641 | spin_lock(&sk->sk_receive_queue.lock); | 638 | spin_lock(&sk->sk_receive_queue.lock); |
642 | h = (struct tpacket_hdr *)packet_lookup_frame(po, po->head); | 639 | h = packet_lookup_frame(po, po->head); |
643 | 640 | ||
644 | if (h->tp_status) | 641 | if (h->tp_status) |
645 | goto ring_is_full; | 642 | goto ring_is_full; |
@@ -1473,7 +1470,7 @@ static int packet_notifier(struct notifier_block *this, unsigned long msg, void | |||
1473 | { | 1470 | { |
1474 | struct sock *sk; | 1471 | struct sock *sk; |
1475 | struct hlist_node *node; | 1472 | struct hlist_node *node; |
1476 | struct net_device *dev = (struct net_device*)data; | 1473 | struct net_device *dev = data; |
1477 | 1474 | ||
1478 | read_lock(&packet_sklist_lock); | 1475 | read_lock(&packet_sklist_lock); |
1479 | sk_for_each(sk, node, &packet_sklist) { | 1476 | sk_for_each(sk, node, &packet_sklist) { |
@@ -1588,7 +1585,7 @@ static unsigned int packet_poll(struct file * file, struct socket *sock, | |||
1588 | unsigned last = po->head ? po->head-1 : po->frame_max; | 1585 | unsigned last = po->head ? po->head-1 : po->frame_max; |
1589 | struct tpacket_hdr *h; | 1586 | struct tpacket_hdr *h; |
1590 | 1587 | ||
1591 | h = (struct tpacket_hdr *)packet_lookup_frame(po, last); | 1588 | h = packet_lookup_frame(po, last); |
1592 | 1589 | ||
1593 | if (h->tp_status) | 1590 | if (h->tp_status) |
1594 | mask |= POLLIN | POLLRDNORM; | 1591 | mask |= POLLIN | POLLRDNORM; |
diff --git a/net/sctp/outqueue.c b/net/sctp/outqueue.c index 5c2ddd10db06..41abfd17627e 100644 --- a/net/sctp/outqueue.c +++ b/net/sctp/outqueue.c | |||
@@ -396,6 +396,19 @@ void sctp_retransmit_mark(struct sctp_outq *q, | |||
396 | if (sctp_chunk_abandoned(chunk)) { | 396 | if (sctp_chunk_abandoned(chunk)) { |
397 | list_del_init(lchunk); | 397 | list_del_init(lchunk); |
398 | sctp_insert_list(&q->abandoned, lchunk); | 398 | sctp_insert_list(&q->abandoned, lchunk); |
399 | |||
400 | /* If this chunk has not been previousely acked, | ||
401 | * stop considering it 'outstanding'. Our peer | ||
402 | * will most likely never see it since it will | ||
403 | * not be retransmitted | ||
404 | */ | ||
405 | if (!chunk->tsn_gap_acked) { | ||
406 | chunk->transport->flight_size -= | ||
407 | sctp_data_size(chunk); | ||
408 | q->outstanding_bytes -= sctp_data_size(chunk); | ||
409 | q->asoc->peer.rwnd += (sctp_data_size(chunk) + | ||
410 | sizeof(struct sk_buff)); | ||
411 | } | ||
399 | continue; | 412 | continue; |
400 | } | 413 | } |
401 | 414 | ||
@@ -1244,6 +1257,15 @@ static void sctp_check_transmitted(struct sctp_outq *q, | |||
1244 | if (sctp_chunk_abandoned(tchunk)) { | 1257 | if (sctp_chunk_abandoned(tchunk)) { |
1245 | /* Move the chunk to abandoned list. */ | 1258 | /* Move the chunk to abandoned list. */ |
1246 | sctp_insert_list(&q->abandoned, lchunk); | 1259 | sctp_insert_list(&q->abandoned, lchunk); |
1260 | |||
1261 | /* If this chunk has not been acked, stop | ||
1262 | * considering it as 'outstanding'. | ||
1263 | */ | ||
1264 | if (!tchunk->tsn_gap_acked) { | ||
1265 | tchunk->transport->flight_size -= | ||
1266 | sctp_data_size(tchunk); | ||
1267 | q->outstanding_bytes -= sctp_data_size(tchunk); | ||
1268 | } | ||
1247 | continue; | 1269 | continue; |
1248 | } | 1270 | } |
1249 | 1271 | ||
@@ -1695,11 +1717,6 @@ static void sctp_generate_fwdtsn(struct sctp_outq *q, __u32 ctsn) | |||
1695 | */ | 1717 | */ |
1696 | if (TSN_lte(tsn, ctsn)) { | 1718 | if (TSN_lte(tsn, ctsn)) { |
1697 | list_del_init(lchunk); | 1719 | list_del_init(lchunk); |
1698 | if (!chunk->tsn_gap_acked) { | ||
1699 | chunk->transport->flight_size -= | ||
1700 | sctp_data_size(chunk); | ||
1701 | q->outstanding_bytes -= sctp_data_size(chunk); | ||
1702 | } | ||
1703 | sctp_chunk_free(chunk); | 1720 | sctp_chunk_free(chunk); |
1704 | } else { | 1721 | } else { |
1705 | if (TSN_lte(tsn, asoc->adv_peer_ack_point+1)) { | 1722 | if (TSN_lte(tsn, asoc->adv_peer_ack_point+1)) { |
diff --git a/net/sctp/sm_statefuns.c b/net/sctp/sm_statefuns.c index b3cad8a03736..70c39eac0581 100644 --- a/net/sctp/sm_statefuns.c +++ b/net/sctp/sm_statefuns.c | |||
@@ -4605,12 +4605,12 @@ sctp_disposition_t sctp_sf_do_6_3_3_rtx(const struct sctp_endpoint *ep, | |||
4605 | * sent as soon as cwnd allows (normally when a SACK arrives). | 4605 | * sent as soon as cwnd allows (normally when a SACK arrives). |
4606 | */ | 4606 | */ |
4607 | 4607 | ||
4608 | /* NB: Rules E4 and F1 are implicit in R1. */ | ||
4609 | sctp_add_cmd_sf(commands, SCTP_CMD_RETRAN, SCTP_TRANSPORT(transport)); | ||
4610 | |||
4611 | /* Do some failure management (Section 8.2). */ | 4608 | /* Do some failure management (Section 8.2). */ |
4612 | sctp_add_cmd_sf(commands, SCTP_CMD_STRIKE, SCTP_TRANSPORT(transport)); | 4609 | sctp_add_cmd_sf(commands, SCTP_CMD_STRIKE, SCTP_TRANSPORT(transport)); |
4613 | 4610 | ||
4611 | /* NB: Rules E4 and F1 are implicit in R1. */ | ||
4612 | sctp_add_cmd_sf(commands, SCTP_CMD_RETRAN, SCTP_TRANSPORT(transport)); | ||
4613 | |||
4614 | return SCTP_DISPOSITION_CONSUME; | 4614 | return SCTP_DISPOSITION_CONSUME; |
4615 | } | 4615 | } |
4616 | 4616 | ||
diff --git a/net/sunrpc/svc.c b/net/sunrpc/svc.c index 4ab137403e1a..8353829bc5c6 100644 --- a/net/sunrpc/svc.c +++ b/net/sunrpc/svc.c | |||
@@ -115,7 +115,7 @@ fail: | |||
115 | static int | 115 | static int |
116 | svc_pool_map_init_percpu(struct svc_pool_map *m) | 116 | svc_pool_map_init_percpu(struct svc_pool_map *m) |
117 | { | 117 | { |
118 | unsigned int maxpools = highest_possible_processor_id()+1; | 118 | unsigned int maxpools = nr_cpu_ids; |
119 | unsigned int pidx = 0; | 119 | unsigned int pidx = 0; |
120 | unsigned int cpu; | 120 | unsigned int cpu; |
121 | int err; | 121 | int err; |
@@ -143,7 +143,7 @@ svc_pool_map_init_percpu(struct svc_pool_map *m) | |||
143 | static int | 143 | static int |
144 | svc_pool_map_init_pernode(struct svc_pool_map *m) | 144 | svc_pool_map_init_pernode(struct svc_pool_map *m) |
145 | { | 145 | { |
146 | unsigned int maxpools = highest_possible_node_id()+1; | 146 | unsigned int maxpools = nr_node_ids; |
147 | unsigned int pidx = 0; | 147 | unsigned int pidx = 0; |
148 | unsigned int node; | 148 | unsigned int node; |
149 | int err; | 149 | int err; |