1 /* 2 * Some IBSS support code for cfg80211. 3 * 4 * Copyright 2009 Johannes Berg <johannes@sipsolutions.net> 5 */ 6 7 #include <linux/etherdevice.h> 8 #include <linux/if_arp.h> 9 #include <linux/slab.h> 10 #include <linux/export.h> 11 #include <net/cfg80211.h> 12 #include "wext-compat.h" 13 #include "nl80211.h" 14 15 16 void __cfg80211_ibss_joined(struct net_device *dev, const u8 *bssid) 17 { 18 struct wireless_dev *wdev = dev->ieee80211_ptr; 19 struct cfg80211_bss *bss; 20 #ifdef CONFIG_CFG80211_WEXT 21 union iwreq_data wrqu; 22 #endif 23 24 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 25 return; 26 27 if (!wdev->ssid_len) 28 return; 29 30 bss = cfg80211_get_bss(wdev->wiphy, NULL, bssid, 31 wdev->ssid, wdev->ssid_len, 32 WLAN_CAPABILITY_IBSS, WLAN_CAPABILITY_IBSS); 33 34 if (WARN_ON(!bss)) 35 return; 36 37 if (wdev->current_bss) { 38 cfg80211_unhold_bss(wdev->current_bss); 39 cfg80211_put_bss(&wdev->current_bss->pub); 40 } 41 42 cfg80211_hold_bss(bss_from_pub(bss)); 43 wdev->current_bss = bss_from_pub(bss); 44 45 wdev->sme_state = CFG80211_SME_CONNECTED; 46 cfg80211_upload_connect_keys(wdev); 47 48 nl80211_send_ibss_bssid(wiphy_to_dev(wdev->wiphy), dev, bssid, 49 GFP_KERNEL); 50 #ifdef CONFIG_CFG80211_WEXT 51 memset(&wrqu, 0, sizeof(wrqu)); 52 memcpy(wrqu.ap_addr.sa_data, bssid, ETH_ALEN); 53 wireless_send_event(dev, SIOCGIWAP, &wrqu, NULL); 54 #endif 55 } 56 57 void cfg80211_ibss_joined(struct net_device *dev, const u8 *bssid, gfp_t gfp) 58 { 59 struct wireless_dev *wdev = dev->ieee80211_ptr; 60 struct cfg80211_registered_device *rdev = wiphy_to_dev(wdev->wiphy); 61 struct cfg80211_event *ev; 62 unsigned long flags; 63 64 CFG80211_DEV_WARN_ON(wdev->sme_state != CFG80211_SME_CONNECTING); 65 66 ev = kzalloc(sizeof(*ev), gfp); 67 if (!ev) 68 return; 69 70 ev->type = EVENT_IBSS_JOINED; 71 memcpy(ev->cr.bssid, bssid, ETH_ALEN); 72 73 spin_lock_irqsave(&wdev->event_lock, flags); 74 list_add_tail(&ev->list, &wdev->event_list); 75 spin_unlock_irqrestore(&wdev->event_lock, flags); 76 queue_work(cfg80211_wq, &rdev->event_work); 77 } 78 EXPORT_SYMBOL(cfg80211_ibss_joined); 79 80 int __cfg80211_join_ibss(struct cfg80211_registered_device *rdev, 81 struct net_device *dev, 82 struct cfg80211_ibss_params *params, 83 struct cfg80211_cached_keys *connkeys) 84 { 85 struct wireless_dev *wdev = dev->ieee80211_ptr; 86 int err; 87 88 ASSERT_WDEV_LOCK(wdev); 89 90 if (wdev->ssid_len) 91 return -EALREADY; 92 93 if (!params->basic_rates) { 94 /* 95 * If no rates were explicitly configured, 96 * use the mandatory rate set for 11b or 97 * 11a for maximum compatibility. 98 */ 99 struct ieee80211_supported_band *sband = 100 rdev->wiphy.bands[params->channel->band]; 101 int j; 102 u32 flag = params->channel->band == IEEE80211_BAND_5GHZ ? 103 IEEE80211_RATE_MANDATORY_A : 104 IEEE80211_RATE_MANDATORY_B; 105 106 for (j = 0; j < sband->n_bitrates; j++) { 107 if (sband->bitrates[j].flags & flag) 108 params->basic_rates |= BIT(j); 109 } 110 } 111 112 if (WARN_ON(wdev->connect_keys)) 113 kfree(wdev->connect_keys); 114 wdev->connect_keys = connkeys; 115 116 #ifdef CONFIG_CFG80211_WEXT 117 wdev->wext.ibss.channel = params->channel; 118 #endif 119 wdev->sme_state = CFG80211_SME_CONNECTING; 120 err = rdev->ops->join_ibss(&rdev->wiphy, dev, params); 121 if (err) { 122 wdev->connect_keys = NULL; 123 wdev->sme_state = CFG80211_SME_IDLE; 124 return err; 125 } 126 127 memcpy(wdev->ssid, params->ssid, params->ssid_len); 128 wdev->ssid_len = params->ssid_len; 129 130 return 0; 131 } 132 133 int cfg80211_join_ibss(struct cfg80211_registered_device *rdev, 134 struct net_device *dev, 135 struct cfg80211_ibss_params *params, 136 struct cfg80211_cached_keys *connkeys) 137 { 138 struct wireless_dev *wdev = dev->ieee80211_ptr; 139 int err; 140 141 mutex_lock(&rdev->devlist_mtx); 142 wdev_lock(wdev); 143 err = __cfg80211_join_ibss(rdev, dev, params, connkeys); 144 wdev_unlock(wdev); 145 mutex_unlock(&rdev->devlist_mtx); 146 147 return err; 148 } 149 150 static void __cfg80211_clear_ibss(struct net_device *dev, bool nowext) 151 { 152 struct wireless_dev *wdev = dev->ieee80211_ptr; 153 struct cfg80211_registered_device *rdev = wiphy_to_dev(wdev->wiphy); 154 int i; 155 156 ASSERT_WDEV_LOCK(wdev); 157 158 kfree(wdev->connect_keys); 159 wdev->connect_keys = NULL; 160 161 /* 162 * Delete all the keys ... pairwise keys can't really 163 * exist any more anyway, but default keys might. 164 */ 165 if (rdev->ops->del_key) 166 for (i = 0; i < 6; i++) 167 rdev->ops->del_key(wdev->wiphy, dev, i, false, NULL); 168 169 if (wdev->current_bss) { 170 cfg80211_unhold_bss(wdev->current_bss); 171 cfg80211_put_bss(&wdev->current_bss->pub); 172 } 173 174 wdev->current_bss = NULL; 175 wdev->sme_state = CFG80211_SME_IDLE; 176 wdev->ssid_len = 0; 177 #ifdef CONFIG_CFG80211_WEXT 178 if (!nowext) 179 wdev->wext.ibss.ssid_len = 0; 180 #endif 181 } 182 183 void cfg80211_clear_ibss(struct net_device *dev, bool nowext) 184 { 185 struct wireless_dev *wdev = dev->ieee80211_ptr; 186 187 wdev_lock(wdev); 188 __cfg80211_clear_ibss(dev, nowext); 189 wdev_unlock(wdev); 190 } 191 192 int __cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, 193 struct net_device *dev, bool nowext) 194 { 195 struct wireless_dev *wdev = dev->ieee80211_ptr; 196 int err; 197 198 ASSERT_WDEV_LOCK(wdev); 199 200 if (!wdev->ssid_len) 201 return -ENOLINK; 202 203 err = rdev->ops->leave_ibss(&rdev->wiphy, dev); 204 205 if (err) 206 return err; 207 208 __cfg80211_clear_ibss(dev, nowext); 209 210 return 0; 211 } 212 213 int cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, 214 struct net_device *dev, bool nowext) 215 { 216 struct wireless_dev *wdev = dev->ieee80211_ptr; 217 int err; 218 219 wdev_lock(wdev); 220 err = __cfg80211_leave_ibss(rdev, dev, nowext); 221 wdev_unlock(wdev); 222 223 return err; 224 } 225 226 #ifdef CONFIG_CFG80211_WEXT 227 int cfg80211_ibss_wext_join(struct cfg80211_registered_device *rdev, 228 struct wireless_dev *wdev) 229 { 230 struct cfg80211_cached_keys *ck = NULL; 231 enum ieee80211_band band; 232 int i, err; 233 234 ASSERT_WDEV_LOCK(wdev); 235 236 if (!wdev->wext.ibss.beacon_interval) 237 wdev->wext.ibss.beacon_interval = 100; 238 239 /* try to find an IBSS channel if none requested ... */ 240 if (!wdev->wext.ibss.channel) { 241 for (band = 0; band < IEEE80211_NUM_BANDS; band++) { 242 struct ieee80211_supported_band *sband; 243 struct ieee80211_channel *chan; 244 245 sband = rdev->wiphy.bands[band]; 246 if (!sband) 247 continue; 248 249 for (i = 0; i < sband->n_channels; i++) { 250 chan = &sband->channels[i]; 251 if (chan->flags & IEEE80211_CHAN_NO_IBSS) 252 continue; 253 if (chan->flags & IEEE80211_CHAN_DISABLED) 254 continue; 255 wdev->wext.ibss.channel = chan; 256 break; 257 } 258 259 if (wdev->wext.ibss.channel) 260 break; 261 } 262 263 if (!wdev->wext.ibss.channel) 264 return -EINVAL; 265 } 266 267 /* don't join -- SSID is not there */ 268 if (!wdev->wext.ibss.ssid_len) 269 return 0; 270 271 if (!netif_running(wdev->netdev)) 272 return 0; 273 274 if (wdev->wext.keys) { 275 wdev->wext.keys->def = wdev->wext.default_key; 276 wdev->wext.keys->defmgmt = wdev->wext.default_mgmt_key; 277 } 278 279 wdev->wext.ibss.privacy = wdev->wext.default_key != -1; 280 281 if (wdev->wext.keys) { 282 ck = kmemdup(wdev->wext.keys, sizeof(*ck), GFP_KERNEL); 283 if (!ck) 284 return -ENOMEM; 285 for (i = 0; i < 6; i++) 286 ck->params[i].key = ck->data[i]; 287 } 288 err = __cfg80211_join_ibss(rdev, wdev->netdev, 289 &wdev->wext.ibss, ck); 290 if (err) 291 kfree(ck); 292 293 return err; 294 } 295 296 int cfg80211_ibss_wext_siwfreq(struct net_device *dev, 297 struct iw_request_info *info, 298 struct iw_freq *wextfreq, char *extra) 299 { 300 struct wireless_dev *wdev = dev->ieee80211_ptr; 301 struct cfg80211_registered_device *rdev = wiphy_to_dev(wdev->wiphy); 302 struct ieee80211_channel *chan = NULL; 303 int err, freq; 304 305 /* call only for ibss! */ 306 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 307 return -EINVAL; 308 309 if (!rdev->ops->join_ibss) 310 return -EOPNOTSUPP; 311 312 freq = cfg80211_wext_freq(wdev->wiphy, wextfreq); 313 if (freq < 0) 314 return freq; 315 316 if (freq) { 317 chan = ieee80211_get_channel(wdev->wiphy, freq); 318 if (!chan) 319 return -EINVAL; 320 if (chan->flags & IEEE80211_CHAN_NO_IBSS || 321 chan->flags & IEEE80211_CHAN_DISABLED) 322 return -EINVAL; 323 } 324 325 if (wdev->wext.ibss.channel == chan) 326 return 0; 327 328 wdev_lock(wdev); 329 err = 0; 330 if (wdev->ssid_len) 331 err = __cfg80211_leave_ibss(rdev, dev, true); 332 wdev_unlock(wdev); 333 334 if (err) 335 return err; 336 337 if (chan) { 338 wdev->wext.ibss.channel = chan; 339 wdev->wext.ibss.channel_fixed = true; 340 } else { 341 /* cfg80211_ibss_wext_join will pick one if needed */ 342 wdev->wext.ibss.channel_fixed = false; 343 } 344 345 mutex_lock(&rdev->devlist_mtx); 346 wdev_lock(wdev); 347 err = cfg80211_ibss_wext_join(rdev, wdev); 348 wdev_unlock(wdev); 349 mutex_unlock(&rdev->devlist_mtx); 350 351 return err; 352 } 353 354 int cfg80211_ibss_wext_giwfreq(struct net_device *dev, 355 struct iw_request_info *info, 356 struct iw_freq *freq, char *extra) 357 { 358 struct wireless_dev *wdev = dev->ieee80211_ptr; 359 struct ieee80211_channel *chan = NULL; 360 361 /* call only for ibss! */ 362 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 363 return -EINVAL; 364 365 wdev_lock(wdev); 366 if (wdev->current_bss) 367 chan = wdev->current_bss->pub.channel; 368 else if (wdev->wext.ibss.channel) 369 chan = wdev->wext.ibss.channel; 370 wdev_unlock(wdev); 371 372 if (chan) { 373 freq->m = chan->center_freq; 374 freq->e = 6; 375 return 0; 376 } 377 378 /* no channel if not joining */ 379 return -EINVAL; 380 } 381 382 int cfg80211_ibss_wext_siwessid(struct net_device *dev, 383 struct iw_request_info *info, 384 struct iw_point *data, char *ssid) 385 { 386 struct wireless_dev *wdev = dev->ieee80211_ptr; 387 struct cfg80211_registered_device *rdev = wiphy_to_dev(wdev->wiphy); 388 size_t len = data->length; 389 int err; 390 391 /* call only for ibss! */ 392 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 393 return -EINVAL; 394 395 if (!rdev->ops->join_ibss) 396 return -EOPNOTSUPP; 397 398 wdev_lock(wdev); 399 err = 0; 400 if (wdev->ssid_len) 401 err = __cfg80211_leave_ibss(rdev, dev, true); 402 wdev_unlock(wdev); 403 404 if (err) 405 return err; 406 407 /* iwconfig uses nul termination in SSID.. */ 408 if (len > 0 && ssid[len - 1] == '\0') 409 len--; 410 411 wdev->wext.ibss.ssid = wdev->ssid; 412 memcpy(wdev->wext.ibss.ssid, ssid, len); 413 wdev->wext.ibss.ssid_len = len; 414 415 mutex_lock(&rdev->devlist_mtx); 416 wdev_lock(wdev); 417 err = cfg80211_ibss_wext_join(rdev, wdev); 418 wdev_unlock(wdev); 419 mutex_unlock(&rdev->devlist_mtx); 420 421 return err; 422 } 423 424 int cfg80211_ibss_wext_giwessid(struct net_device *dev, 425 struct iw_request_info *info, 426 struct iw_point *data, char *ssid) 427 { 428 struct wireless_dev *wdev = dev->ieee80211_ptr; 429 430 /* call only for ibss! */ 431 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 432 return -EINVAL; 433 434 data->flags = 0; 435 436 wdev_lock(wdev); 437 if (wdev->ssid_len) { 438 data->flags = 1; 439 data->length = wdev->ssid_len; 440 memcpy(ssid, wdev->ssid, data->length); 441 } else if (wdev->wext.ibss.ssid && wdev->wext.ibss.ssid_len) { 442 data->flags = 1; 443 data->length = wdev->wext.ibss.ssid_len; 444 memcpy(ssid, wdev->wext.ibss.ssid, data->length); 445 } 446 wdev_unlock(wdev); 447 448 return 0; 449 } 450 451 int cfg80211_ibss_wext_siwap(struct net_device *dev, 452 struct iw_request_info *info, 453 struct sockaddr *ap_addr, char *extra) 454 { 455 struct wireless_dev *wdev = dev->ieee80211_ptr; 456 struct cfg80211_registered_device *rdev = wiphy_to_dev(wdev->wiphy); 457 u8 *bssid = ap_addr->sa_data; 458 int err; 459 460 /* call only for ibss! */ 461 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 462 return -EINVAL; 463 464 if (!rdev->ops->join_ibss) 465 return -EOPNOTSUPP; 466 467 if (ap_addr->sa_family != ARPHRD_ETHER) 468 return -EINVAL; 469 470 /* automatic mode */ 471 if (is_zero_ether_addr(bssid) || is_broadcast_ether_addr(bssid)) 472 bssid = NULL; 473 474 /* both automatic */ 475 if (!bssid && !wdev->wext.ibss.bssid) 476 return 0; 477 478 /* fixed already - and no change */ 479 if (wdev->wext.ibss.bssid && bssid && 480 ether_addr_equal(bssid, wdev->wext.ibss.bssid)) 481 return 0; 482 483 wdev_lock(wdev); 484 err = 0; 485 if (wdev->ssid_len) 486 err = __cfg80211_leave_ibss(rdev, dev, true); 487 wdev_unlock(wdev); 488 489 if (err) 490 return err; 491 492 if (bssid) { 493 memcpy(wdev->wext.bssid, bssid, ETH_ALEN); 494 wdev->wext.ibss.bssid = wdev->wext.bssid; 495 } else 496 wdev->wext.ibss.bssid = NULL; 497 498 mutex_lock(&rdev->devlist_mtx); 499 wdev_lock(wdev); 500 err = cfg80211_ibss_wext_join(rdev, wdev); 501 wdev_unlock(wdev); 502 mutex_unlock(&rdev->devlist_mtx); 503 504 return err; 505 } 506 507 int cfg80211_ibss_wext_giwap(struct net_device *dev, 508 struct iw_request_info *info, 509 struct sockaddr *ap_addr, char *extra) 510 { 511 struct wireless_dev *wdev = dev->ieee80211_ptr; 512 513 /* call only for ibss! */ 514 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) 515 return -EINVAL; 516 517 ap_addr->sa_family = ARPHRD_ETHER; 518 519 wdev_lock(wdev); 520 if (wdev->current_bss) 521 memcpy(ap_addr->sa_data, wdev->current_bss->pub.bssid, ETH_ALEN); 522 else if (wdev->wext.ibss.bssid) 523 memcpy(ap_addr->sa_data, wdev->wext.ibss.bssid, ETH_ALEN); 524 else 525 memset(ap_addr->sa_data, 0, ETH_ALEN); 526 527 wdev_unlock(wdev); 528 529 return 0; 530 } 531 #endif 532