lkml.org 
[lkml]   [2002]   [Mar]   [5]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
Patch in this message
/
Date
Subject[PATCH 2.4.19-pre2] ray_cs : Wireless Extension fix
From
	Hi Marcelo,

This patch fix a known bug of the Raylink driver and make it
properly process setting Wireless Extension. This patch was blessed by
the ray_cs maintainer and has already been included in 2.5.2 (over two
months). I have just tested this patch on the hardware with kernel
2.4.19-pre2.
Would you mind including that in your next kernel release ?

Thanks...

Jean

----------------------------------------------

--- linux/drivers/net/pcmcia/ray_cs-t1.c Thu Dec 13 17:53:39 2001
+++ linux/drivers/net/pcmcia/ray_cs.c Fri Dec 14 11:33:08 2001
@@ -999,7 +999,9 @@ static int ray_event(event_t event, int
/*===========================================================================*/
int ray_dev_init(struct net_device *dev)
{
+#ifdef RAY_IMMEDIATE_INIT
int i;
+#endif /* RAY_IMMEDIATE_INIT */
ray_dev_t *local = dev->priv;
dev_link_t *link = local->finder;

@@ -1008,6 +1010,7 @@ int ray_dev_init(struct net_device *dev)
DEBUG(2,"ray_dev_init - device not present\n");
return -1;
}
+#ifdef RAY_IMMEDIATE_INIT
/* Download startup parameters */
if ( (i = dl_startup_params(dev)) < 0)
{
@@ -1015,7 +1018,14 @@ int ray_dev_init(struct net_device *dev)
"returns 0x%x\n",i);
return -1;
}
-
+#else /* RAY_IMMEDIATE_INIT */
+ /* Postpone the card init so that we can still configure the card,
+ * for example using the Wireless Extensions. The init will happen
+ * in ray_open() - Jean II */
+ DEBUG(1,"ray_dev_init: postponing card init to ray_open() ; Status = %d\n",
+ local->card_status);
+#endif /* RAY_IMMEDIATE_INIT */
+
/* copy mac and broadcast addresses to linux device */
memcpy(&dev->dev_addr, &local->sparm.b4.a_mac_addr, ADDRLEN);
memset(dev->broadcast, 0xff, ETH_ALEN);
@@ -1245,6 +1255,22 @@ static int ray_dev_ioctl(struct net_devi
wrq->u.freq.e = 0;
break;

+ /* Set frequency/channel */
+ case SIOCSIWFREQ:
+ /* Reject if card is already initialised */
+ if(local->card_status != CARD_AWAITING_PARAM)
+ {
+ err = -EBUSY;
+ break;
+ }
+
+ /* Setting by channel number */
+ if ((wrq->u.freq.m > USA_HOP_MOD) || (wrq->u.freq.e > 0))
+ err = -EOPNOTSUPP;
+ else
+ local->sparm.b5.a_hop_pattern = wrq->u.freq.m;
+ break;
+
/* Get current network name (ESSID) */
case SIOCGIWESSID:
if (wrq->u.data.pointer)
@@ -1262,6 +1288,46 @@ static int ray_dev_ioctl(struct net_devi
}
break;

+ /* Set desired network name (ESSID) */
+ case SIOCSIWESSID:
+ /* Reject if card is already initialised */
+ if(local->card_status != CARD_AWAITING_PARAM)
+ {
+ err = -EBUSY;
+ break;
+ }
+
+ if (wrq->u.data.pointer)
+ {
+ char card_essid[IW_ESSID_MAX_SIZE + 1];
+
+ /* Check if we asked for `any' */
+ if(wrq->u.data.flags == 0)
+ {
+ /* Corey : can you do that ? */
+ err = -EOPNOTSUPP;
+ }
+ else
+ {
+ /* Check the size of the string */
+ if(wrq->u.data.length >
+ IW_ESSID_MAX_SIZE + 1)
+ {
+ err = -E2BIG;
+ break;
+ }
+ copy_from_user(card_essid,
+ wrq->u.data.pointer,
+ wrq->u.data.length);
+ card_essid[IW_ESSID_MAX_SIZE] = '\0';
+
+ /* Set the ESSID in the card */
+ memcpy(local->sparm.b5.a_current_ess_id, card_essid,
+ IW_ESSID_MAX_SIZE);
+ }
+ }
+ break;
+
/* Get current Access Point (BSSID in our case) */
case SIOCGIWAP:
memcpy(wrq->u.ap_addr.sa_data, local->bss_id, ETH_ALEN);
@@ -1304,6 +1370,34 @@ static int ray_dev_ioctl(struct net_devi
wrq->u.rts.fixed = 1;
break;

+ /* Set the desired RTS threshold */
+ case SIOCSIWRTS:
+ {
+ int rthr = wrq->u.rts.value;
+
+ /* Reject if card is already initialised */
+ if(local->card_status != CARD_AWAITING_PARAM)
+ {
+ err = -EBUSY;
+ break;
+ }
+
+ /* if(wrq->u.rts.fixed == 0) we should complain */
+#if WIRELESS_EXT > 8
+ if(wrq->u.rts.disabled)
+ rthr = 32767;
+ else
+#endif /* WIRELESS_EXT > 8 */
+ if((rthr < 0) || (rthr > 2347)) /* What's the max packet size ??? */
+ {
+ err = -EINVAL;
+ break;
+ }
+ local->sparm.b5.a_rts_threshold[0] = (rthr >> 8) & 0xFF;
+ local->sparm.b5.a_rts_threshold[1] = rthr & 0xFF;
+ }
+ break;
+
/* Get the current fragmentation threshold */
case SIOCGIWFRAG:
wrq->u.frag.value = (local->sparm.b5.a_frag_threshold[0] << 8)
@@ -1313,6 +1407,35 @@ static int ray_dev_ioctl(struct net_devi
#endif /* WIRELESS_EXT > 8 */
wrq->u.frag.fixed = 1;
break;
+
+ /* Set the desired fragmentation threshold */
+ case SIOCSIWFRAG:
+ {
+ int fthr = wrq->u.frag.value;
+
+ /* Reject if card is already initialised */
+ if(local->card_status != CARD_AWAITING_PARAM)
+ {
+ err = -EBUSY;
+ break;
+ }
+
+ /* if(wrq->u.frag.fixed == 0) should complain */
+#if WIRELESS_EXT > 8
+ if(wrq->u.frag.disabled)
+ fthr = 32767;
+ else
+#endif /* WIRELESS_EXT > 8 */
+ if((fthr < 256) || (fthr > 2347)) /* To check out ! */
+ {
+ err = -EINVAL;
+ break;
+ }
+ local->sparm.b5.a_frag_threshold[0] = (fthr >> 8) & 0xFF;
+ local->sparm.b5.a_frag_threshold[1] = fthr & 0xFF;
+ }
+ break;
+
#endif /* WIRELESS_EXT > 7 */
#if WIRELESS_EXT > 8

@@ -1323,6 +1446,33 @@ static int ray_dev_ioctl(struct net_devi
else
wrq->u.mode = IW_MODE_ADHOC;
break;
+
+ /* Set the current mode of operation */
+ case SIOCSIWMODE:
+ {
+ char card_mode = 1;
+
+ /* Reject if card is already initialised */
+ if(local->card_status != CARD_AWAITING_PARAM)
+ {
+ err = -EBUSY;
+ break;
+ }
+
+ switch (wrq->u.mode)
+ {
+ case IW_MODE_ADHOC:
+ card_mode = 0;
+ // Fall through
+ case IW_MODE_INFRA:
+ local->sparm.b5.a_network_type = card_mode;
+ break;
+ default:
+ err = -EINVAL;
+ }
+ }
+ break;
+
#endif /* WIRELESS_EXT > 8 */
#if WIRELESS_EXT > 7
/* ------------------ IWSPY SUPPORT ------------------ */
@@ -1549,6 +1699,21 @@ static int ray_open(struct net_device *d
if (link->open == 0) local->num_multi = 0;
link->open++;

+ /* If the card is not started, time to start it ! - Jean II */
+ if(local->card_status == CARD_AWAITING_PARAM) {
+ int i;
+
+ DEBUG(1,"ray_open: doing init now !\n");
+
+ /* Download startup parameters */
+ if ( (i = dl_startup_params(dev)) < 0)
+ {
+ printk(KERN_INFO "ray_dev_init dl_startup_params failed - "
+ "returns 0x%x\n",i);
+ return -1;
+ }
+ }
+
if (sniffer) netif_stop_queue(dev);
else netif_start_queue(dev);

@@ -1571,6 +1736,11 @@ static int ray_dev_close(struct net_devi
netif_stop_queue(dev);
if (link->state & DEV_STALE_CONFIG)
mod_timer(&link->release, jiffies + HZ/20);
+
+ /* In here, we should stop the hardware (stop card from beeing active)
+ * and set local->card_status to CARD_AWAITING_PARAM, so that while the
+ * card is closed we can chage its configuration.
+ * Probably also need a COR reset to get sane state - Jean II */

MOD_DEC_USE_COUNT;

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/

\
 
 \ /
  Last update: 2005-03-22 13:24    [W:0.043 / U:0.096 seconds]
©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site