aboutsummaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
authorMauro Carvalho Chehab <mchehab@redhat.com>2012-10-25 05:15:34 -0400
committerMauro Carvalho Chehab <mchehab@redhat.com>2012-10-25 05:15:34 -0400
commit285019fd95540c92e3348d43c699110458cd133c (patch)
treed949b55f5992a0d3dff88fe8e1de11523dce2acb /net
parentdeb09ddaff1435f72dd598d38f9b58354c68a5ec (diff)
parenta0d271cbfed1dd50278c6b06bead3d00ba0a88f9 (diff)
Merge tag 'v3.6' into fixes
Linux 3.6 * tag 'v3.6': (91 commits) Linux 3.6 vfs: dcache: fix deadlock in tree traversal mtdchar: fix offset overflow detection thp: avoid VM_BUG_ON page_count(page) false positives in __collapse_huge_page_copy iommu/amd: Fix wrong assumption in iommu-group specific code netdev: octeon: fix return value check in octeon_mgmt_init_phy() ALSA: snd-usb: fix next_packet_size calls for pause case inetpeer: fix token initialization qlcnic: Fix scheduling while atomic bug bnx2: Clean up remaining iounmap trivial select_parent documentation fix net: phy: smsc: Implement PHY config_init for LAN87xx smsc75xx: fix resume after device reset um: Preinclude include/linux/kern_levels.h um: Fix IPC on um netdev: pasemi: fix return value check in pasemi_mac_phy_init() team: fix return value check l2tp: fix return value check USB: Fix race condition when removing host controllers USB: ohci-at91: fix null pointer in ohci_hcd_at91_overcurrent_irq ...
Diffstat (limited to 'net')
-rw-r--r--net/batman-adv/bat_iv_ogm.c13
-rw-r--r--net/batman-adv/soft-interface.c7
-rw-r--r--net/bluetooth/hci_core.c2
-rw-r--r--net/bluetooth/l2cap_core.c2
-rw-r--r--net/bluetooth/mgmt.c16
-rw-r--r--net/ceph/messenger.c5
-rw-r--r--net/core/sock.c3
-rw-r--r--net/ipv4/inetpeer.c5
-rw-r--r--net/ipv4/raw.c14
-rw-r--r--net/ipv6/mip6.c20
-rw-r--r--net/ipv6/raw.c21
-rw-r--r--net/l2tp/l2tp_netlink.c12
-rw-r--r--net/netfilter/xt_limit.c8
-rw-r--r--net/wireless/reg.c12
14 files changed, 86 insertions, 54 deletions
diff --git a/net/batman-adv/bat_iv_ogm.c b/net/batman-adv/bat_iv_ogm.c
index e877af8bdd1e..469daabd90c7 100644
--- a/net/batman-adv/bat_iv_ogm.c
+++ b/net/batman-adv/bat_iv_ogm.c
@@ -642,7 +642,8 @@ batadv_iv_ogm_orig_update(struct batadv_priv *bat_priv,
642 struct batadv_neigh_node *router = NULL; 642 struct batadv_neigh_node *router = NULL;
643 struct batadv_orig_node *orig_node_tmp; 643 struct batadv_orig_node *orig_node_tmp;
644 struct hlist_node *node; 644 struct hlist_node *node;
645 uint8_t bcast_own_sum_orig, bcast_own_sum_neigh; 645 int if_num;
646 uint8_t sum_orig, sum_neigh;
646 uint8_t *neigh_addr; 647 uint8_t *neigh_addr;
647 648
648 batadv_dbg(BATADV_DBG_BATMAN, bat_priv, 649 batadv_dbg(BATADV_DBG_BATMAN, bat_priv,
@@ -727,17 +728,17 @@ batadv_iv_ogm_orig_update(struct batadv_priv *bat_priv,
727 if (router && (neigh_node->tq_avg == router->tq_avg)) { 728 if (router && (neigh_node->tq_avg == router->tq_avg)) {
728 orig_node_tmp = router->orig_node; 729 orig_node_tmp = router->orig_node;
729 spin_lock_bh(&orig_node_tmp->ogm_cnt_lock); 730 spin_lock_bh(&orig_node_tmp->ogm_cnt_lock);
730 bcast_own_sum_orig = 731 if_num = router->if_incoming->if_num;
731 orig_node_tmp->bcast_own_sum[if_incoming->if_num]; 732 sum_orig = orig_node_tmp->bcast_own_sum[if_num];
732 spin_unlock_bh(&orig_node_tmp->ogm_cnt_lock); 733 spin_unlock_bh(&orig_node_tmp->ogm_cnt_lock);
733 734
734 orig_node_tmp = neigh_node->orig_node; 735 orig_node_tmp = neigh_node->orig_node;
735 spin_lock_bh(&orig_node_tmp->ogm_cnt_lock); 736 spin_lock_bh(&orig_node_tmp->ogm_cnt_lock);
736 bcast_own_sum_neigh = 737 if_num = neigh_node->if_incoming->if_num;
737 orig_node_tmp->bcast_own_sum[if_incoming->if_num]; 738 sum_neigh = orig_node_tmp->bcast_own_sum[if_num];
738 spin_unlock_bh(&orig_node_tmp->ogm_cnt_lock); 739 spin_unlock_bh(&orig_node_tmp->ogm_cnt_lock);
739 740
740 if (bcast_own_sum_orig >= bcast_own_sum_neigh) 741 if (sum_orig >= sum_neigh)
741 goto update_tt; 742 goto update_tt;
742 } 743 }
743 744
diff --git a/net/batman-adv/soft-interface.c b/net/batman-adv/soft-interface.c
index 109ea2aae96c..21c53577c8d6 100644
--- a/net/batman-adv/soft-interface.c
+++ b/net/batman-adv/soft-interface.c
@@ -100,18 +100,21 @@ static int batadv_interface_set_mac_addr(struct net_device *dev, void *p)
100{ 100{
101 struct batadv_priv *bat_priv = netdev_priv(dev); 101 struct batadv_priv *bat_priv = netdev_priv(dev);
102 struct sockaddr *addr = p; 102 struct sockaddr *addr = p;
103 uint8_t old_addr[ETH_ALEN];
103 104
104 if (!is_valid_ether_addr(addr->sa_data)) 105 if (!is_valid_ether_addr(addr->sa_data))
105 return -EADDRNOTAVAIL; 106 return -EADDRNOTAVAIL;
106 107
108 memcpy(old_addr, dev->dev_addr, ETH_ALEN);
109 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
110
107 /* only modify transtable if it has been initialized before */ 111 /* only modify transtable if it has been initialized before */
108 if (atomic_read(&bat_priv->mesh_state) == BATADV_MESH_ACTIVE) { 112 if (atomic_read(&bat_priv->mesh_state) == BATADV_MESH_ACTIVE) {
109 batadv_tt_local_remove(bat_priv, dev->dev_addr, 113 batadv_tt_local_remove(bat_priv, old_addr,
110 "mac address changed", false); 114 "mac address changed", false);
111 batadv_tt_local_add(dev, addr->sa_data, BATADV_NULL_IFINDEX); 115 batadv_tt_local_add(dev, addr->sa_data, BATADV_NULL_IFINDEX);
112 } 116 }
113 117
114 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN);
115 dev->addr_assign_type &= ~NET_ADDR_RANDOM; 118 dev->addr_assign_type &= ~NET_ADDR_RANDOM;
116 return 0; 119 return 0;
117} 120}
diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c
index d4de5db18d5a..0b997c8f9655 100644
--- a/net/bluetooth/hci_core.c
+++ b/net/bluetooth/hci_core.c
@@ -734,6 +734,8 @@ static int hci_dev_do_close(struct hci_dev *hdev)
734 734
735 cancel_work_sync(&hdev->le_scan); 735 cancel_work_sync(&hdev->le_scan);
736 736
737 cancel_delayed_work(&hdev->power_off);
738
737 hci_req_cancel(hdev, ENODEV); 739 hci_req_cancel(hdev, ENODEV);
738 hci_req_lock(hdev); 740 hci_req_lock(hdev);
739 741
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index 4ea1710a4783..38c00f142203 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -1008,7 +1008,7 @@ static void l2cap_send_disconn_req(struct l2cap_conn *conn, struct l2cap_chan *c
1008 if (!conn) 1008 if (!conn)
1009 return; 1009 return;
1010 1010
1011 if (chan->mode == L2CAP_MODE_ERTM) { 1011 if (chan->mode == L2CAP_MODE_ERTM && chan->state == BT_CONNECTED) {
1012 __clear_retrans_timer(chan); 1012 __clear_retrans_timer(chan);
1013 __clear_monitor_timer(chan); 1013 __clear_monitor_timer(chan);
1014 __clear_ack_timer(chan); 1014 __clear_ack_timer(chan);
diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c
index ad6613d17ca6..eba022de3c20 100644
--- a/net/bluetooth/mgmt.c
+++ b/net/bluetooth/mgmt.c
@@ -2875,6 +2875,22 @@ int mgmt_powered(struct hci_dev *hdev, u8 powered)
2875 if (scan) 2875 if (scan)
2876 hci_send_cmd(hdev, HCI_OP_WRITE_SCAN_ENABLE, 1, &scan); 2876 hci_send_cmd(hdev, HCI_OP_WRITE_SCAN_ENABLE, 1, &scan);
2877 2877
2878 if (test_bit(HCI_SSP_ENABLED, &hdev->dev_flags)) {
2879 u8 ssp = 1;
2880
2881 hci_send_cmd(hdev, HCI_OP_WRITE_SSP_MODE, 1, &ssp);
2882 }
2883
2884 if (test_bit(HCI_LE_ENABLED, &hdev->dev_flags)) {
2885 struct hci_cp_write_le_host_supported cp;
2886
2887 cp.le = 1;
2888 cp.simul = !!(hdev->features[6] & LMP_SIMUL_LE_BR);
2889
2890 hci_send_cmd(hdev, HCI_OP_WRITE_LE_HOST_SUPPORTED,
2891 sizeof(cp), &cp);
2892 }
2893
2878 update_class(hdev); 2894 update_class(hdev);
2879 update_name(hdev, hdev->dev_name); 2895 update_name(hdev, hdev->dev_name);
2880 update_eir(hdev); 2896 update_eir(hdev);
diff --git a/net/ceph/messenger.c b/net/ceph/messenger.c
index 24c5eea8c45b..159aa8bef9e7 100644
--- a/net/ceph/messenger.c
+++ b/net/ceph/messenger.c
@@ -1073,16 +1073,13 @@ static int write_partial_msg_pages(struct ceph_connection *con)
1073 BUG_ON(kaddr == NULL); 1073 BUG_ON(kaddr == NULL);
1074 base = kaddr + con->out_msg_pos.page_pos + bio_offset; 1074 base = kaddr + con->out_msg_pos.page_pos + bio_offset;
1075 crc = crc32c(crc, base, len); 1075 crc = crc32c(crc, base, len);
1076 kunmap(page);
1076 msg->footer.data_crc = cpu_to_le32(crc); 1077 msg->footer.data_crc = cpu_to_le32(crc);
1077 con->out_msg_pos.did_page_crc = true; 1078 con->out_msg_pos.did_page_crc = true;
1078 } 1079 }
1079 ret = ceph_tcp_sendpage(con->sock, page, 1080 ret = ceph_tcp_sendpage(con->sock, page,
1080 con->out_msg_pos.page_pos + bio_offset, 1081 con->out_msg_pos.page_pos + bio_offset,
1081 len, 1); 1082 len, 1);
1082
1083 if (do_datacrc)
1084 kunmap(page);
1085
1086 if (ret <= 0) 1083 if (ret <= 0)
1087 goto out; 1084 goto out;
1088 1085
diff --git a/net/core/sock.c b/net/core/sock.c
index 305792076121..a6000fbad294 100644
--- a/net/core/sock.c
+++ b/net/core/sock.c
@@ -691,7 +691,8 @@ set_rcvbuf:
691 691
692 case SO_KEEPALIVE: 692 case SO_KEEPALIVE:
693#ifdef CONFIG_INET 693#ifdef CONFIG_INET
694 if (sk->sk_protocol == IPPROTO_TCP) 694 if (sk->sk_protocol == IPPROTO_TCP &&
695 sk->sk_type == SOCK_STREAM)
695 tcp_set_keepalive(sk, valbool); 696 tcp_set_keepalive(sk, valbool);
696#endif 697#endif
697 sock_valbool_flag(sk, SOCK_KEEPOPEN, valbool); 698 sock_valbool_flag(sk, SOCK_KEEPOPEN, valbool);
diff --git a/net/ipv4/inetpeer.c b/net/ipv4/inetpeer.c
index e1e0a4e8fd34..c7527f6b9ad9 100644
--- a/net/ipv4/inetpeer.c
+++ b/net/ipv4/inetpeer.c
@@ -510,7 +510,10 @@ relookup:
510 secure_ipv6_id(daddr->addr.a6)); 510 secure_ipv6_id(daddr->addr.a6));
511 p->metrics[RTAX_LOCK-1] = INETPEER_METRICS_NEW; 511 p->metrics[RTAX_LOCK-1] = INETPEER_METRICS_NEW;
512 p->rate_tokens = 0; 512 p->rate_tokens = 0;
513 p->rate_last = 0; 513 /* 60*HZ is arbitrary, but chosen enough high so that the first
514 * calculation of tokens is at its maximum.
515 */
516 p->rate_last = jiffies - 60*HZ;
514 INIT_LIST_HEAD(&p->gc_list); 517 INIT_LIST_HEAD(&p->gc_list);
515 518
516 /* Link the node. */ 519 /* Link the node. */
diff --git a/net/ipv4/raw.c b/net/ipv4/raw.c
index ff0f071969ea..d23c6571ba1c 100644
--- a/net/ipv4/raw.c
+++ b/net/ipv4/raw.c
@@ -131,18 +131,20 @@ found:
131 * 0 - deliver 131 * 0 - deliver
132 * 1 - block 132 * 1 - block
133 */ 133 */
134static __inline__ int icmp_filter(struct sock *sk, struct sk_buff *skb) 134static int icmp_filter(const struct sock *sk, const struct sk_buff *skb)
135{ 135{
136 int type; 136 struct icmphdr _hdr;
137 const struct icmphdr *hdr;
137 138
138 if (!pskb_may_pull(skb, sizeof(struct icmphdr))) 139 hdr = skb_header_pointer(skb, skb_transport_offset(skb),
140 sizeof(_hdr), &_hdr);
141 if (!hdr)
139 return 1; 142 return 1;
140 143
141 type = icmp_hdr(skb)->type; 144 if (hdr->type < 32) {
142 if (type < 32) {
143 __u32 data = raw_sk(sk)->filter.data; 145 __u32 data = raw_sk(sk)->filter.data;
144 146
145 return ((1 << type) & data) != 0; 147 return ((1U << hdr->type) & data) != 0;
146 } 148 }
147 149
148 /* Do not block unknown ICMP types */ 150 /* Do not block unknown ICMP types */
diff --git a/net/ipv6/mip6.c b/net/ipv6/mip6.c
index 5b087c31d87b..0f9bdc5ee9f3 100644
--- a/net/ipv6/mip6.c
+++ b/net/ipv6/mip6.c
@@ -86,28 +86,30 @@ static int mip6_mh_len(int type)
86 86
87static int mip6_mh_filter(struct sock *sk, struct sk_buff *skb) 87static int mip6_mh_filter(struct sock *sk, struct sk_buff *skb)
88{ 88{
89 struct ip6_mh *mh; 89 struct ip6_mh _hdr;
90 const struct ip6_mh *mh;
90 91
91 if (!pskb_may_pull(skb, (skb_transport_offset(skb)) + 8) || 92 mh = skb_header_pointer(skb, skb_transport_offset(skb),
92 !pskb_may_pull(skb, (skb_transport_offset(skb) + 93 sizeof(_hdr), &_hdr);
93 ((skb_transport_header(skb)[1] + 1) << 3)))) 94 if (!mh)
94 return -1; 95 return -1;
95 96
96 mh = (struct ip6_mh *)skb_transport_header(skb); 97 if (((mh->ip6mh_hdrlen + 1) << 3) > skb->len)
98 return -1;
97 99
98 if (mh->ip6mh_hdrlen < mip6_mh_len(mh->ip6mh_type)) { 100 if (mh->ip6mh_hdrlen < mip6_mh_len(mh->ip6mh_type)) {
99 LIMIT_NETDEBUG(KERN_DEBUG "mip6: MH message too short: %d vs >=%d\n", 101 LIMIT_NETDEBUG(KERN_DEBUG "mip6: MH message too short: %d vs >=%d\n",
100 mh->ip6mh_hdrlen, mip6_mh_len(mh->ip6mh_type)); 102 mh->ip6mh_hdrlen, mip6_mh_len(mh->ip6mh_type));
101 mip6_param_prob(skb, 0, ((&mh->ip6mh_hdrlen) - 103 mip6_param_prob(skb, 0, offsetof(struct ip6_mh, ip6mh_hdrlen) +
102 skb_network_header(skb))); 104 skb_network_header_len(skb));
103 return -1; 105 return -1;
104 } 106 }
105 107
106 if (mh->ip6mh_proto != IPPROTO_NONE) { 108 if (mh->ip6mh_proto != IPPROTO_NONE) {
107 LIMIT_NETDEBUG(KERN_DEBUG "mip6: MH invalid payload proto = %d\n", 109 LIMIT_NETDEBUG(KERN_DEBUG "mip6: MH invalid payload proto = %d\n",
108 mh->ip6mh_proto); 110 mh->ip6mh_proto);
109 mip6_param_prob(skb, 0, ((&mh->ip6mh_proto) - 111 mip6_param_prob(skb, 0, offsetof(struct ip6_mh, ip6mh_proto) +
110 skb_network_header(skb))); 112 skb_network_header_len(skb));
111 return -1; 113 return -1;
112 } 114 }
113 115
diff --git a/net/ipv6/raw.c b/net/ipv6/raw.c
index ef0579d5bca6..4a5f78b50495 100644
--- a/net/ipv6/raw.c
+++ b/net/ipv6/raw.c
@@ -107,21 +107,20 @@ found:
107 * 0 - deliver 107 * 0 - deliver
108 * 1 - block 108 * 1 - block
109 */ 109 */
110static __inline__ int icmpv6_filter(struct sock *sk, struct sk_buff *skb) 110static int icmpv6_filter(const struct sock *sk, const struct sk_buff *skb)
111{ 111{
112 struct icmp6hdr *icmph; 112 struct icmp6hdr *_hdr;
113 struct raw6_sock *rp = raw6_sk(sk); 113 const struct icmp6hdr *hdr;
114
115 if (pskb_may_pull(skb, sizeof(struct icmp6hdr))) {
116 __u32 *data = &rp->filter.data[0];
117 int bit_nr;
118 114
119 icmph = (struct icmp6hdr *) skb->data; 115 hdr = skb_header_pointer(skb, skb_transport_offset(skb),
120 bit_nr = icmph->icmp6_type; 116 sizeof(_hdr), &_hdr);
117 if (hdr) {
118 const __u32 *data = &raw6_sk(sk)->filter.data[0];
119 unsigned int type = hdr->icmp6_type;
121 120
122 return (data[bit_nr >> 5] & (1 << (bit_nr & 31))) != 0; 121 return (data[type >> 5] & (1U << (type & 31))) != 0;
123 } 122 }
124 return 0; 123 return 1;
125} 124}
126 125
127#if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE) 126#if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
diff --git a/net/l2tp/l2tp_netlink.c b/net/l2tp/l2tp_netlink.c
index d71cd9229a47..6f936358d664 100644
--- a/net/l2tp/l2tp_netlink.c
+++ b/net/l2tp/l2tp_netlink.c
@@ -80,8 +80,8 @@ static int l2tp_nl_cmd_noop(struct sk_buff *skb, struct genl_info *info)
80 80
81 hdr = genlmsg_put(msg, info->snd_pid, info->snd_seq, 81 hdr = genlmsg_put(msg, info->snd_pid, info->snd_seq,
82 &l2tp_nl_family, 0, L2TP_CMD_NOOP); 82 &l2tp_nl_family, 0, L2TP_CMD_NOOP);
83 if (IS_ERR(hdr)) { 83 if (!hdr) {
84 ret = PTR_ERR(hdr); 84 ret = -EMSGSIZE;
85 goto err_out; 85 goto err_out;
86 } 86 }
87 87
@@ -250,8 +250,8 @@ static int l2tp_nl_tunnel_send(struct sk_buff *skb, u32 pid, u32 seq, int flags,
250 250
251 hdr = genlmsg_put(skb, pid, seq, &l2tp_nl_family, flags, 251 hdr = genlmsg_put(skb, pid, seq, &l2tp_nl_family, flags,
252 L2TP_CMD_TUNNEL_GET); 252 L2TP_CMD_TUNNEL_GET);
253 if (IS_ERR(hdr)) 253 if (!hdr)
254 return PTR_ERR(hdr); 254 return -EMSGSIZE;
255 255
256 if (nla_put_u8(skb, L2TP_ATTR_PROTO_VERSION, tunnel->version) || 256 if (nla_put_u8(skb, L2TP_ATTR_PROTO_VERSION, tunnel->version) ||
257 nla_put_u32(skb, L2TP_ATTR_CONN_ID, tunnel->tunnel_id) || 257 nla_put_u32(skb, L2TP_ATTR_CONN_ID, tunnel->tunnel_id) ||
@@ -617,8 +617,8 @@ static int l2tp_nl_session_send(struct sk_buff *skb, u32 pid, u32 seq, int flags
617 sk = tunnel->sock; 617 sk = tunnel->sock;
618 618
619 hdr = genlmsg_put(skb, pid, seq, &l2tp_nl_family, flags, L2TP_CMD_SESSION_GET); 619 hdr = genlmsg_put(skb, pid, seq, &l2tp_nl_family, flags, L2TP_CMD_SESSION_GET);
620 if (IS_ERR(hdr)) 620 if (!hdr)
621 return PTR_ERR(hdr); 621 return -EMSGSIZE;
622 622
623 if (nla_put_u32(skb, L2TP_ATTR_CONN_ID, tunnel->tunnel_id) || 623 if (nla_put_u32(skb, L2TP_ATTR_CONN_ID, tunnel->tunnel_id) ||
624 nla_put_u32(skb, L2TP_ATTR_SESSION_ID, session->session_id) || 624 nla_put_u32(skb, L2TP_ATTR_SESSION_ID, session->session_id) ||
diff --git a/net/netfilter/xt_limit.c b/net/netfilter/xt_limit.c
index 5c22ce8ab309..a4c1e4528cac 100644
--- a/net/netfilter/xt_limit.c
+++ b/net/netfilter/xt_limit.c
@@ -117,11 +117,11 @@ static int limit_mt_check(const struct xt_mtchk_param *par)
117 117
118 /* For SMP, we only want to use one set of state. */ 118 /* For SMP, we only want to use one set of state. */
119 r->master = priv; 119 r->master = priv;
120 /* User avg in seconds * XT_LIMIT_SCALE: convert to jiffies *
121 128. */
122 priv->prev = jiffies;
123 priv->credit = user2credits(r->avg * r->burst); /* Credits full. */
120 if (r->cost == 0) { 124 if (r->cost == 0) {
121 /* User avg in seconds * XT_LIMIT_SCALE: convert to jiffies *
122 128. */
123 priv->prev = jiffies;
124 priv->credit = user2credits(r->avg * r->burst); /* Credits full. */
125 r->credit_cap = priv->credit; /* Credits full. */ 125 r->credit_cap = priv->credit; /* Credits full. */
126 r->cost = user2credits(r->avg); 126 r->cost = user2credits(r->avg);
127 } 127 }
diff --git a/net/wireless/reg.c b/net/wireless/reg.c
index 2ded3c7fad06..72d170ca3406 100644
--- a/net/wireless/reg.c
+++ b/net/wireless/reg.c
@@ -350,6 +350,9 @@ static void reg_regdb_search(struct work_struct *work)
350 struct reg_regdb_search_request *request; 350 struct reg_regdb_search_request *request;
351 const struct ieee80211_regdomain *curdom, *regdom; 351 const struct ieee80211_regdomain *curdom, *regdom;
352 int i, r; 352 int i, r;
353 bool set_reg = false;
354
355 mutex_lock(&cfg80211_mutex);
353 356
354 mutex_lock(&reg_regdb_search_mutex); 357 mutex_lock(&reg_regdb_search_mutex);
355 while (!list_empty(&reg_regdb_search_list)) { 358 while (!list_empty(&reg_regdb_search_list)) {
@@ -365,9 +368,7 @@ static void reg_regdb_search(struct work_struct *work)
365 r = reg_copy_regd(&regdom, curdom); 368 r = reg_copy_regd(&regdom, curdom);
366 if (r) 369 if (r)
367 break; 370 break;
368 mutex_lock(&cfg80211_mutex); 371 set_reg = true;
369 set_regdom(regdom);
370 mutex_unlock(&cfg80211_mutex);
371 break; 372 break;
372 } 373 }
373 } 374 }
@@ -375,6 +376,11 @@ static void reg_regdb_search(struct work_struct *work)
375 kfree(request); 376 kfree(request);
376 } 377 }
377 mutex_unlock(&reg_regdb_search_mutex); 378 mutex_unlock(&reg_regdb_search_mutex);
379
380 if (set_reg)
381 set_regdom(regdom);
382
383 mutex_unlock(&cfg80211_mutex);
378} 384}
379 385
380static DECLARE_WORK(reg_regdb_work, reg_regdb_search); 386static DECLARE_WORK(reg_regdb_work, reg_regdb_search);