Esempio n. 1
0
static void pnp_assign_dma(struct pnp_dev *dev, struct pnp_dma *rule, int idx)
{
    struct pnp_resource *pnp_res;
    struct resource *res;
    int i;

    /* DMA priority: this table is good for i386 */
    static unsigned short xtab[8] = {
        1, 3, 5, 6, 7, 0, 2, 4
    };

    pnp_res = pnp_get_pnp_resource(dev, IORESOURCE_DMA, idx);
    if (!pnp_res) {
        dev_err(&dev->dev, "too many DMA resources\n");
        return;
    }

    res = &pnp_res->res;

    /* check if this resource has been manually set, if so skip */
    if (!(res->flags & IORESOURCE_AUTO)) {
        dev_dbg(&dev->dev, "  dma %d already set to %d flags %#lx\n",
            idx, (int) res->start, res->flags);
        return;
    }

    /* set the initial values */
    pnp_res->index = idx;
    res->flags |= rule->flags | IORESOURCE_DMA;
    res->flags &= ~IORESOURCE_UNSET;

    for (i = 0; i < 8; i++) {
        if (rule->map & (1 << xtab[i])) {
            res->start = res->end = xtab[i];
            if (pnp_check_dma(dev, res)) {
                dev_dbg(&dev->dev, "  assign dma %d %d\n", idx,
                    (int) res->start);
                return;
            }
        }
    }
#ifdef MAX_DMA_CHANNELS
    res->start = res->end = MAX_DMA_CHANNELS;
#endif
    res->flags |= IORESOURCE_UNSET | IORESOURCE_DISABLED;
    dev_dbg(&dev->dev, "  disable dma %d\n", idx);
}
Esempio n. 2
0
static int pnp_assign_dma(struct pnp_dev *dev, struct pnp_dma *rule, int idx)
{
	unsigned long *start, *end, *flags;
	int i;

	/* DMA priority: this table is good for i386 */
	static unsigned short xtab[8] = {
		1, 3, 5, 6, 7, 0, 2, 4
	};

	if (!dev || !rule)
		return -EINVAL;

	if (idx >= PNP_MAX_DMA) {
		pnp_err("More than 2 dmas is incompatible with pnp specifications.");
		/* pretend we were successful so at least the manager won't try again */
		return 1;
	}

	/* check if this resource has been manually set, if so skip */
	if (!(dev->res.dma_resource[idx].flags & IORESOURCE_AUTO))
		return 1;

	start = &dev->res.dma_resource[idx].start;
	end = &dev->res.dma_resource[idx].end;
	flags = &dev->res.dma_resource[idx].flags;

	/* set the initial values */
	*flags |= rule->flags | IORESOURCE_DMA;
	*flags &=  ~IORESOURCE_UNSET;

	if (!rule->map) {
		*flags |= IORESOURCE_DISABLED;
		return 1; /* skip disabled resource requests */
	}

	for (i = 0; i < 8; i++) {
		if(rule->map & (1<<xtab[i])) {
			*start = *end = xtab[i];
			if(pnp_check_dma(dev, idx))
				return 1;
		}
	}
	return 0;
}
Esempio n. 3
0
/**
 * pnp_manual_config_dev - Disables Auto Config and Manually sets the resource table
 * @dev: pointer to the desired device
 * @res: pointer to the new resource config
 * @mode: 0 or PNP_CONFIG_FORCE
 *
 * This function can be used by drivers that want to manually set thier resources.
 */
int pnp_manual_config_dev(struct pnp_dev *dev, struct pnp_resource_table * res, int mode)
{
	int i;
	struct pnp_resource_table * bak;
	if (!dev || !res)
		return -EINVAL;
	if (!pnp_can_configure(dev))
		return -ENODEV;
	bak = pnp_alloc(sizeof(struct pnp_resource_table));
	if (!bak)
		return -ENOMEM;
	*bak = dev->res;

	down(&pnp_res_mutex);
	dev->res = *res;
	if (!(mode & PNP_CONFIG_FORCE)) {
		for (i = 0; i < PNP_MAX_PORT; i++) {
			if(!pnp_check_port(dev,i))
				goto fail;
		}
		for (i = 0; i < PNP_MAX_MEM; i++) {
			if(!pnp_check_mem(dev,i))
				goto fail;
		}
		for (i = 0; i < PNP_MAX_IRQ; i++) {
			if(!pnp_check_irq(dev,i))
				goto fail;
		}
		for (i = 0; i < PNP_MAX_DMA; i++) {
			if(!pnp_check_dma(dev,i))
				goto fail;
		}
	}
	up(&pnp_res_mutex);

	kfree(bak);
	return 0;

fail:
	dev->res = *bak;
	up(&pnp_res_mutex);
	kfree(bak);
	return -EINVAL;
}
Esempio n. 4
0
static void pnp_assign_dma(struct pnp_dev *dev, struct pnp_dma *rule, int idx)
{
	resource_size_t *start, *end;
	unsigned long *flags;
	int i;

	/* DMA priority: this table is good for i386 */
	static unsigned short xtab[8] = {
		1, 3, 5, 6, 7, 0, 2, 4
	};

	if (idx >= PNP_MAX_DMA) {
		dev_err(&dev->dev, "too many DMA resources\n");
		return;
	}

	/* check if this resource has been manually set, if so skip */
	if (!(dev->res.dma_resource[idx].flags & IORESOURCE_AUTO))
		return;

	start = &dev->res.dma_resource[idx].start;
	end = &dev->res.dma_resource[idx].end;
	flags = &dev->res.dma_resource[idx].flags;

	/* set the initial values */
	*flags |= rule->flags | IORESOURCE_DMA;
	*flags &= ~IORESOURCE_UNSET;

	for (i = 0; i < 8; i++) {
		if (rule->map & (1 << xtab[i])) {
			*start = *end = xtab[i];
			if (pnp_check_dma(dev, idx))
				return;
		}
	}
#ifdef MAX_DMA_CHANNELS
	*start = *end = MAX_DMA_CHANNELS;
#endif
	*flags |= IORESOURCE_UNSET | IORESOURCE_DISABLED;
}