Ejemplo n.º 1
0
/*
 * Reset the card using configuration registers COR and CCSR.
 * If IDLE is 1, stop the firmware, so that it can be safely rewritten.
 */
static int
spectrum_reset(struct pcmcia_device *link, int idle)
{
	int last_ret, last_fn;
	conf_reg_t reg;
	u_int save_cor;

	/* Doing it if hardware is gone is guaranteed crash */
	if (!pcmcia_dev_present(link))
		return -ENODEV;

	/* Save original COR value */
	reg.Function = 0;
	reg.Action = CS_READ;
	reg.Offset = CISREG_COR;
	CS_CHECK(AccessConfigurationRegister,
		 pcmcia_access_configuration_register(link, &reg));
	save_cor = reg.Value;

	/* Soft-Reset card */
	reg.Action = CS_WRITE;
	reg.Offset = CISREG_COR;
	reg.Value = (save_cor | COR_SOFT_RESET);
	CS_CHECK(AccessConfigurationRegister,
		 pcmcia_access_configuration_register(link, &reg));
	udelay(1000);

	/* Read CCSR */
	reg.Action = CS_READ;
	reg.Offset = CISREG_CCSR;
	CS_CHECK(AccessConfigurationRegister,
		 pcmcia_access_configuration_register(link, &reg));

	/*
	 * Start or stop the firmware.  Memory width bit should be
	 * preserved from the value we've just read.
	 */
	reg.Action = CS_WRITE;
	reg.Offset = CISREG_CCSR;
	reg.Value = (idle ? HCR_IDLE : HCR_RUN) | (reg.Value & HCR_MEM16);
	CS_CHECK(AccessConfigurationRegister,
		 pcmcia_access_configuration_register(link, &reg));
	udelay(1000);

	/* Restore original COR configuration index */
	reg.Action = CS_WRITE;
	reg.Offset = CISREG_COR;
	reg.Value = (save_cor & ~COR_SOFT_RESET);
	CS_CHECK(AccessConfigurationRegister,
		 pcmcia_access_configuration_register(link, &reg));
	udelay(1000);
	return 0;

      cs_failed:
	cs_error(link, last_fn, last_ret);
	return -ENODEV;
}
Ejemplo n.º 2
0
/* ----------------------------------------------------------------------------
nmclan_reset
	Reset and restore all of the Xilinx and MACE registers.
---------------------------------------------------------------------------- */
static void nmclan_reset(struct net_device *dev)
{
  mace_private *lp = netdev_priv(dev);

#if RESET_XILINX
  struct pcmcia_device *link = &lp->link;
  conf_reg_t reg;
  u_long OrigCorValue; 

  /* Save original COR value */
  reg.Function = 0;
  reg.Action = CS_READ;
  reg.Offset = CISREG_COR;
  reg.Value = 0;
  pcmcia_access_configuration_register(link, &reg);
  OrigCorValue = reg.Value;

  /* Reset Xilinx */
  reg.Action = CS_WRITE;
  reg.Offset = CISREG_COR;
  DEBUG(1, "nmclan_reset: OrigCorValue=0x%lX, resetting...\n",
	OrigCorValue);
  reg.Value = COR_SOFT_RESET;
  pcmcia_access_configuration_register(link, &reg);
  /* Need to wait for 20 ms for PCMCIA to finish reset. */

  /* Restore original COR configuration index */
  reg.Value = COR_LEVEL_REQ | (OrigCorValue & COR_CONFIG_MASK);
  pcmcia_access_configuration_register(link, &reg);
  /* Xilinx is now completely reset along with the MACE chip. */
  lp->tx_free_frames=AM2150_MAX_TX_FRAMES;

#endif /* #if RESET_XILINX */

  /* Xilinx is now completely reset along with the MACE chip. */
  lp->tx_free_frames=AM2150_MAX_TX_FRAMES;

  /* Reinitialize the MACE chip for operation. */
  mace_init(lp, dev->base_addr, dev->dev_addr);
  mace_write(lp, dev->base_addr, MACE_IMR, MACE_IMR_DEFAULT);

  /* Restore the multicast list and enable TX and RX. */
  restore_multicast_list(dev);
} /* nmclan_reset */
Ejemplo n.º 3
0
static int quirk_post_ibm(struct pcmcia_device *link)
{
	conf_reg_t reg = { 0, CS_READ, 0x800, 0 };
	int last_ret, last_fn;

	last_ret = pcmcia_access_configuration_register(link, &reg);
	if (last_ret) {
		last_fn = AccessConfigurationRegister;
		goto cs_failed;
	}
	reg.Action = CS_WRITE;
	reg.Value = reg.Value | 1;
	last_ret = pcmcia_access_configuration_register(link, &reg);
	if (last_ret) {
		last_fn = AccessConfigurationRegister;
		goto cs_failed;
	}
	return 0;

 cs_failed:
	cs_error(link, last_fn, last_ret);
	return -ENODEV;
}
Ejemplo n.º 4
0
int hfa384x_corereset(hfa384x_t *hw, int holdtime, int settletime, int genesis)
{
	int		result = 0;
	conf_reg_t	reg;
	UINT8		corsave;
	DBFENTER;

	WLAN_LOG_DEBUG(3, "Doing reset via CardServices().\n");

	/* Collect COR */
	reg.Function = 0;
	reg.Action = CS_READ;
	reg.Offset = CISREG_COR;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,16)
	result = pcmcia_access_configuration_register(hw->pdev, &reg);
#else
	result = pcmcia_access_configuration_register(
			hw->link->handle,
			&reg);
#endif
	if (result != CS_SUCCESS ) {
		WLAN_LOG_ERROR(
			":0: AccessConfigurationRegister(CS_READ) failed,"
			"result=%d.\n", result);
		result = -EIO;
	}
	corsave = reg.Value;

	/* Write reset bit (BIT7) */
	reg.Value |= BIT7;
	reg.Action = CS_WRITE;
	reg.Offset = CISREG_COR;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,16)
	result = pcmcia_access_configuration_register(hw->pdev, &reg);
#else
	result = pcmcia_access_configuration_register(
			hw->link->handle,
			&reg);
#endif
	if (result != CS_SUCCESS ) {
		WLAN_LOG_ERROR(
			":1: AccessConfigurationRegister(CS_WRITE) failed,"
			"result=%d.\n", result);
		result = -EIO;
	}

	/* Hold for holdtime */
	mdelay(holdtime);

	if (genesis) {
		reg.Value = genesis;
		reg.Action = CS_WRITE;
		reg.Offset = CISREG_CCSR;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,16)
		result = pcmcia_access_configuration_register(hw->pdev, &reg);
#else
		result = pcmcia_access_configuration_register(
				      hw->link->handle,
				      &reg);
#endif
		if (result != CS_SUCCESS ) {
			WLAN_LOG_ERROR(
				":1: AccessConfigurationRegister(CS_WRITE) failed,"
				"result=%d.\n", result);
			result = -EIO;
		}
	}

	/* Hold for holdtime */
	mdelay(holdtime);

	/* Clear reset bit */
	reg.Value &= ~BIT7;
	reg.Action = CS_WRITE;
	reg.Offset = CISREG_COR;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,16)
	result = pcmcia_access_configuration_register(hw->pdev, &reg);
#else
	result = pcmcia_access_configuration_register(
				      hw->link->handle,
				      &reg);
#endif
	if (result != CS_SUCCESS ) {
		WLAN_LOG_ERROR(
			":2: AccessConfigurationRegister(CS_WRITE) failed,"
			"result=%d.\n", result);
		result = -EIO;
		goto done;
	}

	/* Wait for settletime */
	mdelay(settletime);

	/* Set non-reset bits back what they were */
	reg.Value = corsave;
	reg.Action = CS_WRITE;
	reg.Offset = CISREG_COR;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,16)
	result = pcmcia_access_configuration_register(hw->pdev, &reg);
#else
	result = pcmcia_access_configuration_register(
				      hw->link->handle,
				      &reg);
#endif
	if (result != CS_SUCCESS ) {
		WLAN_LOG_ERROR(
			":2: AccessConfigurationRegister(CS_WRITE) failed,"
			"result=%d.\n", result);
		result = -EIO;
		goto done;
	}

done:
	DBFEXIT;
	return result;
}
Ejemplo n.º 5
0
static int ds_ioctl(struct inode * inode, struct file * file,
		    u_int cmd, u_long arg)
{
    socket_t i = minor(inode->i_rdev);
    socket_info_t *s;
    u_int size;
    int ret, err;
    ds_ioctl_arg_t buf;

    DEBUG(2, "ds_ioctl(socket %d, %#x, %#lx)\n", i, cmd, arg);
    
    if ((i >= sockets) || (sockets == 0))
	return -ENODEV;
    s = &socket_table[i];
    
    size = (cmd & IOCSIZE_MASK) >> IOCSIZE_SHIFT;
    if (size > sizeof(ds_ioctl_arg_t)) return -EINVAL;

    /* Permission check */
    if (!(cmd & IOC_OUT) && !capable(CAP_SYS_ADMIN))
	return -EPERM;
	
    if (cmd & IOC_IN) {
	err = verify_area(VERIFY_READ, (char *)arg, size);
	if (err) {
	    DEBUG(3, "ds_ioctl(): verify_read = %d\n", err);
	    return err;
	}
    }
    if (cmd & IOC_OUT) {
	err = verify_area(VERIFY_WRITE, (char *)arg, size);
	if (err) {
	    DEBUG(3, "ds_ioctl(): verify_write = %d\n", err);
	    return err;
	}
    }
    
    err = ret = 0;
    
    if (cmd & IOC_IN) copy_from_user((char *)&buf, (char *)arg, size);
    
    switch (cmd) {
    case DS_ADJUST_RESOURCE_INFO:
	ret = pcmcia_adjust_resource_info(s->handle, &buf.adjust);
	break;
    case DS_GET_CARD_SERVICES_INFO:
	ret = pcmcia_get_card_services_info(&buf.servinfo);
	break;
    case DS_GET_CONFIGURATION_INFO:
	ret = pcmcia_get_configuration_info(s->handle, &buf.config);
	break;
    case DS_GET_FIRST_TUPLE:
	ret = pcmcia_get_first_tuple(s->handle, &buf.tuple);
	break;
    case DS_GET_NEXT_TUPLE:
	ret = pcmcia_get_next_tuple(s->handle, &buf.tuple);
	break;
    case DS_GET_TUPLE_DATA:
	buf.tuple.TupleData = buf.tuple_parse.data;
	buf.tuple.TupleDataMax = sizeof(buf.tuple_parse.data);
	ret = pcmcia_get_tuple_data(s->handle, &buf.tuple);
	break;
    case DS_PARSE_TUPLE:
	buf.tuple.TupleData = buf.tuple_parse.data;
	ret = pcmcia_parse_tuple(s->handle, &buf.tuple, &buf.tuple_parse.parse);
	break;
    case DS_RESET_CARD:
	ret = pcmcia_reset_card(s->handle, NULL);
	break;
    case DS_GET_STATUS:
	ret = pcmcia_get_status(s->handle, &buf.status);
	break;
    case DS_VALIDATE_CIS:
	ret = pcmcia_validate_cis(s->handle, &buf.cisinfo);
	break;
    case DS_SUSPEND_CARD:
	ret = pcmcia_suspend_card(s->handle, NULL);
	break;
    case DS_RESUME_CARD:
	ret = pcmcia_resume_card(s->handle, NULL);
	break;
    case DS_EJECT_CARD:
	ret = pcmcia_eject_card(s->handle, NULL);
	break;
    case DS_INSERT_CARD:
	ret = pcmcia_insert_card(s->handle, NULL);
	break;
    case DS_ACCESS_CONFIGURATION_REGISTER:
	if ((buf.conf_reg.Action == CS_WRITE) && !capable(CAP_SYS_ADMIN))
	    return -EPERM;
	ret = pcmcia_access_configuration_register(s->handle, &buf.conf_reg);
	break;
    case DS_GET_FIRST_REGION:
        ret = pcmcia_get_first_region(s->handle, &buf.region);
	break;
    case DS_GET_NEXT_REGION:
	ret = pcmcia_get_next_region(s->handle, &buf.region);
	break;
    case DS_GET_FIRST_WINDOW:
	buf.win_info.handle = (window_handle_t)s->handle;
	ret = pcmcia_get_first_window(&buf.win_info.handle, &buf.win_info.window);
	break;
    case DS_GET_NEXT_WINDOW:
	ret = pcmcia_get_next_window(&buf.win_info.handle, &buf.win_info.window);
	break;
    case DS_GET_MEM_PAGE:
	ret = pcmcia_get_mem_page(buf.win_info.handle,
			   &buf.win_info.map);
	break;
    case DS_REPLACE_CIS:
	ret = pcmcia_replace_cis(s->handle, &buf.cisdump);
	break;
    case DS_BIND_REQUEST:
	if (!capable(CAP_SYS_ADMIN)) return -EPERM;
	err = bind_request(i, &buf.bind_info);
	break;
    case DS_GET_DEVICE_INFO:
	err = get_device_info(i, &buf.bind_info, 1);
	break;
    case DS_GET_NEXT_DEVICE:
	err = get_device_info(i, &buf.bind_info, 0);
	break;
    case DS_UNBIND_REQUEST:
	err = unbind_request(i, &buf.bind_info);
	break;
    case DS_BIND_MTD:
	if (!suser()) return -EPERM;
	err = bind_mtd(i, &buf.mtd_info);
	break;
    default:
	err = -EINVAL;
    }
    
    if ((err == 0) && (ret != CS_SUCCESS)) {
	DEBUG(2, "ds_ioctl: ret = %d\n", ret);
	switch (ret) {
	case CS_BAD_SOCKET: case CS_NO_CARD:
	    err = -ENODEV; break;
	case CS_BAD_ARGS: case CS_BAD_ATTRIBUTE: case CS_BAD_IRQ:
	case CS_BAD_TUPLE:
	    err = -EINVAL; break;
	case CS_IN_USE:
	    err = -EBUSY; break;
	case CS_OUT_OF_RESOURCE:
	    err = -ENOSPC; break;
	case CS_NO_MORE_ITEMS:
	    err = -ENODATA; break;
	case CS_UNSUPPORTED_FUNCTION:
	    err = -ENOSYS; break;
	default:
	    err = -EIO; break;
	}
    }
    
    if (cmd & IOC_OUT) copy_to_user((char *)arg, (char *)&buf, size);
     
    return err;
} /* ds_ioctl */