aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/airo.c
diff options
context:
space:
mode:
authorDan Williams <dcbw@redhat.com>2006-01-30 11:58:00 -0500
committerJohn W. Linville <linville@tuxdriver.com>2006-01-30 20:35:35 -0500
commit4be757dd4c00ddabff2d6faf639466bb5d76bc79 (patch)
tree2b8d8bc23889da7c78db7592db2f791ef13bcf43 /drivers/net/wireless/airo.c
parentdd5eeb461ea572f82d34e1f2c4b88037df5afedb (diff)
[PATCH] wireless/airo: add IWENCODEEXT and IWAUTH support
This patch adds IWENCODEEXT and IWAUTH support to the airo driver for WEP and unencrypted operation. No WPA though. It allows the driver to operate more willingly with wpa_supplicant and NetworkManager. Signed-off-by: Dan Williams <dcbw@redhat.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers/net/wireless/airo.c')
-rw-r--r--drivers/net/wireless/airo.c276
1 files changed, 274 insertions, 2 deletions
diff --git a/drivers/net/wireless/airo.c b/drivers/net/wireless/airo.c
index 9c577f7b6e58..ef6495b07890 100644
--- a/drivers/net/wireless/airo.c
+++ b/drivers/net/wireless/airo.c
@@ -5756,11 +5756,13 @@ static int airo_set_wap(struct net_device *dev,
5756 Cmd cmd; 5756 Cmd cmd;
5757 Resp rsp; 5757 Resp rsp;
5758 APListRid APList_rid; 5758 APListRid APList_rid;
5759 static const unsigned char bcast[ETH_ALEN] = { 255, 255, 255, 255, 255, 255 }; 5759 static const u8 any[ETH_ALEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
5760 static const u8 off[ETH_ALEN] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
5760 5761
5761 if (awrq->sa_family != ARPHRD_ETHER) 5762 if (awrq->sa_family != ARPHRD_ETHER)
5762 return -EINVAL; 5763 return -EINVAL;
5763 else if (!memcmp(bcast, awrq->sa_data, ETH_ALEN)) { 5764 else if (!memcmp(any, awrq->sa_data, ETH_ALEN) ||
5765 !memcmp(off, awrq->sa_data, ETH_ALEN)) {
5764 memset(&cmd, 0, sizeof(cmd)); 5766 memset(&cmd, 0, sizeof(cmd));
5765 cmd.cmd=CMD_LOSE_SYNC; 5767 cmd.cmd=CMD_LOSE_SYNC;
5766 if (down_interruptible(&local->sem)) 5768 if (down_interruptible(&local->sem))
@@ -6251,6 +6253,267 @@ static int airo_get_encode(struct net_device *dev,
6251 6253
6252/*------------------------------------------------------------------*/ 6254/*------------------------------------------------------------------*/
6253/* 6255/*
6256 * Wireless Handler : set extended Encryption parameters
6257 */
6258static int airo_set_encodeext(struct net_device *dev,
6259 struct iw_request_info *info,
6260 union iwreq_data *wrqu,
6261 char *extra)
6262{
6263 struct airo_info *local = dev->priv;
6264 struct iw_point *encoding = &wrqu->encoding;
6265 struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
6266 CapabilityRid cap_rid; /* Card capability info */
6267 int perm = ( encoding->flags & IW_ENCODE_TEMP ? 0 : 1 );
6268 u16 currentAuthType = local->config.authType;
6269 int idx, key_len, alg = ext->alg; /* Check encryption mode */
6270 wep_key_t key;
6271
6272 /* Is WEP supported ? */
6273 readCapabilityRid(local, &cap_rid, 1);
6274 /* Older firmware doesn't support this...
6275 if(!(cap_rid.softCap & 2)) {
6276 return -EOPNOTSUPP;
6277 } */
6278 readConfigRid(local, 1);
6279
6280 /* Determine and validate the key index */
6281 idx = encoding->flags & IW_ENCODE_INDEX;
6282 if (idx) {
6283 if (idx < 1 || idx > ((cap_rid.softCap & 0x80) ? 4:1))
6284 return -EINVAL;
6285 idx--;
6286 } else
6287 idx = get_wep_key(local, 0xffff);
6288
6289 if (encoding->flags & IW_ENCODE_DISABLED)
6290 alg = IW_ENCODE_ALG_NONE;
6291
6292 /* Just setting the transmit key? */
6293 if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
6294 set_wep_key(local, idx, NULL, 0, perm, 1);
6295 } else {
6296 /* Set the requested key first */
6297 memset(key.key, 0, MAX_KEY_SIZE);
6298 switch (alg) {
6299 case IW_ENCODE_ALG_NONE:
6300 key.len = 0;
6301 break;
6302 case IW_ENCODE_ALG_WEP:
6303 if (ext->key_len > MIN_KEY_SIZE) {
6304 key.len = MAX_KEY_SIZE;
6305 } else if (ext->key_len > 0) {
6306 key.len = MIN_KEY_SIZE;
6307 } else {
6308 return -EINVAL;
6309 }
6310 key_len = min (ext->key_len, key.len);
6311 memcpy(key.key, ext->key, key_len);
6312 break;
6313 default:
6314 return -EINVAL;
6315 }
6316 /* Send the key to the card */
6317 set_wep_key(local, idx, key.key, key.len, perm, 1);
6318 }
6319
6320 /* Read the flags */
6321 if(encoding->flags & IW_ENCODE_DISABLED)
6322 local->config.authType = AUTH_OPEN; // disable encryption
6323 if(encoding->flags & IW_ENCODE_RESTRICTED)
6324 local->config.authType = AUTH_SHAREDKEY; // Only Both
6325 if(encoding->flags & IW_ENCODE_OPEN)
6326 local->config.authType = AUTH_ENCRYPT; // Only Wep
6327 /* Commit the changes to flags if needed */
6328 if (local->config.authType != currentAuthType)
6329 set_bit (FLAG_COMMIT, &local->flags);
6330
6331 return -EINPROGRESS;
6332}
6333
6334
6335/*------------------------------------------------------------------*/
6336/*
6337 * Wireless Handler : get extended Encryption parameters
6338 */
6339static int airo_get_encodeext(struct net_device *dev,
6340 struct iw_request_info *info,
6341 union iwreq_data *wrqu,
6342 char *extra)
6343{
6344 struct airo_info *local = dev->priv;
6345 struct iw_point *encoding = &wrqu->encoding;
6346 struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
6347 CapabilityRid cap_rid; /* Card capability info */
6348 int idx, max_key_len;
6349
6350 /* Is it supported ? */
6351 readCapabilityRid(local, &cap_rid, 1);
6352 if(!(cap_rid.softCap & 2)) {
6353 return -EOPNOTSUPP;
6354 }
6355 readConfigRid(local, 1);
6356
6357 max_key_len = encoding->length - sizeof(*ext);
6358 if (max_key_len < 0)
6359 return -EINVAL;
6360
6361 idx = encoding->flags & IW_ENCODE_INDEX;
6362 if (idx) {
6363 if (idx < 1 || idx > ((cap_rid.softCap & 0x80) ? 4:1))
6364 return -EINVAL;
6365 idx--;
6366 } else
6367 idx = get_wep_key(local, 0xffff);
6368
6369 encoding->flags = idx + 1;
6370 memset(ext, 0, sizeof(*ext));
6371
6372 /* Check encryption mode */
6373 switch(local->config.authType) {
6374 case AUTH_ENCRYPT:
6375 encoding->flags = IW_ENCODE_ALG_WEP | IW_ENCODE_ENABLED;
6376 break;
6377 case AUTH_SHAREDKEY:
6378 encoding->flags = IW_ENCODE_ALG_WEP | IW_ENCODE_ENABLED;
6379 break;
6380 default:
6381 case AUTH_OPEN:
6382 encoding->flags = IW_ENCODE_ALG_NONE | IW_ENCODE_DISABLED;
6383 break;
6384 }
6385 /* We can't return the key, so set the proper flag and return zero */
6386 encoding->flags |= IW_ENCODE_NOKEY;
6387 memset(extra, 0, 16);
6388
6389 /* Copy the key to the user buffer */
6390 ext->key_len = get_wep_key(local, idx);
6391 if (ext->key_len > 16) {
6392 ext->key_len=0;
6393 }
6394
6395 return 0;
6396}
6397
6398
6399/*------------------------------------------------------------------*/
6400/*
6401 * Wireless Handler : set extended authentication parameters
6402 */
6403static int airo_set_auth(struct net_device *dev,
6404 struct iw_request_info *info,
6405 union iwreq_data *wrqu, char *extra)
6406{
6407 struct airo_info *local = dev->priv;
6408 struct iw_param *param = &wrqu->param;
6409 u16 currentAuthType = local->config.authType;
6410
6411 switch (param->flags & IW_AUTH_INDEX) {
6412 case IW_AUTH_WPA_VERSION:
6413 case IW_AUTH_CIPHER_PAIRWISE:
6414 case IW_AUTH_CIPHER_GROUP:
6415 case IW_AUTH_KEY_MGMT:
6416 case IW_AUTH_RX_UNENCRYPTED_EAPOL:
6417 case IW_AUTH_PRIVACY_INVOKED:
6418 /*
6419 * airo does not use these parameters
6420 */
6421 break;
6422
6423 case IW_AUTH_DROP_UNENCRYPTED:
6424 if (param->value) {
6425 /* Only change auth type if unencrypted */
6426 if (currentAuthType == AUTH_OPEN)
6427 local->config.authType = AUTH_ENCRYPT;
6428 } else {
6429 local->config.authType = AUTH_OPEN;
6430 }
6431
6432 /* Commit the changes to flags if needed */
6433 if (local->config.authType != currentAuthType)
6434 set_bit (FLAG_COMMIT, &local->flags);
6435 break;
6436
6437 case IW_AUTH_80211_AUTH_ALG: {
6438 /* FIXME: What about AUTH_OPEN? This API seems to
6439 * disallow setting our auth to AUTH_OPEN.
6440 */
6441 if (param->value & IW_AUTH_ALG_SHARED_KEY) {
6442 local->config.authType = AUTH_SHAREDKEY;
6443 } else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM) {
6444 local->config.authType = AUTH_ENCRYPT;
6445 } else
6446 return -EINVAL;
6447 break;
6448
6449 /* Commit the changes to flags if needed */
6450 if (local->config.authType != currentAuthType)
6451 set_bit (FLAG_COMMIT, &local->flags);
6452 }
6453
6454 case IW_AUTH_WPA_ENABLED:
6455 /* Silently accept disable of WPA */
6456 if (param->value > 0)
6457 return -EOPNOTSUPP;
6458 break;
6459
6460 default:
6461 return -EOPNOTSUPP;
6462 }
6463 return -EINPROGRESS;
6464}
6465
6466
6467/*------------------------------------------------------------------*/
6468/*
6469 * Wireless Handler : get extended authentication parameters
6470 */
6471static int airo_get_auth(struct net_device *dev,
6472 struct iw_request_info *info,
6473 union iwreq_data *wrqu, char *extra)
6474{
6475 struct airo_info *local = dev->priv;
6476 struct iw_param *param = &wrqu->param;
6477 u16 currentAuthType = local->config.authType;
6478
6479 switch (param->flags & IW_AUTH_INDEX) {
6480 case IW_AUTH_DROP_UNENCRYPTED:
6481 switch (currentAuthType) {
6482 case AUTH_SHAREDKEY:
6483 case AUTH_ENCRYPT:
6484 param->value = 1;
6485 break;
6486 default:
6487 param->value = 0;
6488 break;
6489 }
6490 break;
6491
6492 case IW_AUTH_80211_AUTH_ALG:
6493 switch (currentAuthType) {
6494 case AUTH_SHAREDKEY:
6495 param->value = IW_AUTH_ALG_SHARED_KEY;
6496 break;
6497 case AUTH_ENCRYPT:
6498 default:
6499 param->value = IW_AUTH_ALG_OPEN_SYSTEM;
6500 break;
6501 }
6502 break;
6503
6504 case IW_AUTH_WPA_ENABLED:
6505 param->value = 0;
6506 break;
6507
6508 default:
6509 return -EOPNOTSUPP;
6510 }
6511 return 0;
6512}
6513
6514
6515/*------------------------------------------------------------------*/
6516/*
6254 * Wireless Handler : set Tx-Power 6517 * Wireless Handler : set Tx-Power
6255 */ 6518 */
6256static int airo_set_txpow(struct net_device *dev, 6519static int airo_set_txpow(struct net_device *dev,
@@ -7005,6 +7268,15 @@ static const iw_handler airo_handler[] =
7005 (iw_handler) airo_get_encode, /* SIOCGIWENCODE */ 7268 (iw_handler) airo_get_encode, /* SIOCGIWENCODE */
7006 (iw_handler) airo_set_power, /* SIOCSIWPOWER */ 7269 (iw_handler) airo_set_power, /* SIOCSIWPOWER */
7007 (iw_handler) airo_get_power, /* SIOCGIWPOWER */ 7270 (iw_handler) airo_get_power, /* SIOCGIWPOWER */
7271 (iw_handler) NULL, /* -- hole -- */
7272 (iw_handler) NULL, /* -- hole -- */
7273 (iw_handler) NULL, /* SIOCSIWGENIE */
7274 (iw_handler) NULL, /* SIOCGIWGENIE */
7275 (iw_handler) airo_set_auth, /* SIOCSIWAUTH */
7276 (iw_handler) airo_get_auth, /* SIOCGIWAUTH */
7277 (iw_handler) airo_set_encodeext, /* SIOCSIWENCODEEXT */
7278 (iw_handler) airo_get_encodeext, /* SIOCGIWENCODEEXT */
7279 (iw_handler) NULL, /* SIOCSIWPMKSA */
7008}; 7280};
7009 7281
7010/* Note : don't describe AIROIDIFC and AIROOLDIDIFC in here. 7282/* Note : don't describe AIROIDIFC and AIROOLDIDIFC in here.