Example #1
0
static int pca953x_gpio_direction_output(struct gpio_chip *gc,
        unsigned off, int val)
{
    struct pca953x_chip *chip;
    uint16_t reg_val;
    int ret;

    chip = container_of(gc, struct pca953x_chip, gpio_chip);

    /* set output level */
    if (val)
        reg_val = chip->reg_output | (1u << off);
    else
        reg_val = chip->reg_output & ~(1u << off);

    ret = pca953x_write_reg(chip, PCA953X_OUTPUT, reg_val);
    if (ret)
        return ret;

    chip->reg_output = reg_val;

    /* then direction */
    reg_val = chip->reg_direction & ~(1u << off);
    ret = pca953x_write_reg(chip, PCA953X_DIRECTION, reg_val);
    if (ret)
        return ret;

    chip->reg_direction = reg_val;
    return 0;
}
Example #2
0
static int __devinit pca953x_probe(struct i2c_client *client,
				   const struct i2c_device_id *id)
{
	struct pca953x_platform_data *pdata;
	struct pca953x_chip *chip;
	int ret;

	pdata = client->dev.platform_data;
	if (pdata == NULL) {
		dev_dbg(&client->dev, "no platform data\n");
		return -EINVAL;
	}

	chip = kzalloc(sizeof(struct pca953x_chip), GFP_KERNEL);
	if (chip == NULL)
		return -ENOMEM;

	chip->client = client;

	chip->gpio_start = pdata->gpio_base;

	/* initialize cached registers from their original values.
	 * we can't share this chip with another i2c master.
	 */
	pca953x_setup_gpio(chip, id->driver_data);

	ret = pca953x_read_reg(chip, PCA953X_OUTPUT, &chip->reg_output);
	if (ret)
		goto out_failed;

	ret = pca953x_read_reg(chip, PCA953X_DIRECTION, &chip->reg_direction);
	if (ret)
		goto out_failed;

	/* set platform specific polarity inversion */
	ret = pca953x_write_reg(chip, PCA953X_INVERT, pdata->invert);
	if (ret)
		goto out_failed;


	ret = gpiochip_add(&chip->gpio_chip);
	if (ret)
		goto out_failed;

	if (pdata->setup) {
		ret = pdata->setup(client, chip->gpio_chip.base,
				chip->gpio_chip.ngpio, pdata->context);
		if (ret < 0)
			dev_warn(&client->dev, "setup failed, %d\n", ret);
	}

	i2c_set_clientdata(client, chip);
	return 0;

out_failed:
	kfree(chip);
	return ret;
}
Example #3
0
static int pca953x_resume(struct i2c_client *client)
{
	struct pca953x_platform_data *pdata = client->dev.platform_data;
	struct pca953x_chip *chip = i2c_get_clientdata(client);
	uint16_t reg_val;
	int ret = 0;

	/* set platform specific polarity inversion */
	ret = pca953x_write_reg(chip, PCA953X_INVERT, pdata->invert);
	if (ret)
		return ret;

	ret = pca953x_write_reg(chip, PCA953X_OUTPUT, chip->reg_output);
	if (ret)
		return ret;

	ret = pca953x_write_reg(chip, PCA953X_DIRECTION, chip->reg_direction);

	if (ret)
		return ret;

	ret = pca953x_read_reg(chip, PCA953X_INPUT, &reg_val);
	return ret;
}
Example #4
0
static int pca953x_gpio_direction_input(struct gpio_chip *gc, unsigned off)
{
    struct pca953x_chip *chip;
    uint16_t reg_val;
    int ret;

    chip = container_of(gc, struct pca953x_chip, gpio_chip);

    reg_val = chip->reg_direction | (1u << off);
    ret = pca953x_write_reg(chip, PCA953X_DIRECTION, reg_val);
    if (ret)
        return ret;

    chip->reg_direction = reg_val;
    return 0;
}
Example #5
0
static void pca953x_gpio_set_value(struct gpio_chip *gc, unsigned off, int val)
{
    struct pca953x_chip *chip;
    uint16_t reg_val;
    int ret;

    chip = container_of(gc, struct pca953x_chip, gpio_chip);

    if (val)
        reg_val = chip->reg_output | (1u << off);
    else
        reg_val = chip->reg_output & ~(1u << off);

    ret = pca953x_write_reg(chip, PCA953X_OUTPUT, reg_val);
    if (ret)
        return;

    chip->reg_output = reg_val;
}
Example #6
0
static int pca953x_gpio_direction_input(struct gpio_chip *gc, unsigned off)
{
	struct pca953x_chip *chip;
	uint16_t reg_val;
	int ret;

	chip = container_of(gc, struct pca953x_chip, gpio_chip);

	mutex_lock(&chip->i2c_lock);
	reg_val = chip->reg_direction | (1u << off);
	ret = pca953x_write_reg(chip, PCA953X_DIRECTION, reg_val);
	if (ret)
		goto exit;

	chip->reg_direction = reg_val;
	ret = 0;
exit:
	mutex_unlock(&chip->i2c_lock);
	return ret;
}
Example #7
0
static int __devinit pca953x_probe(struct i2c_client *client)
{
	struct pca953x_platform_data *pdata;
	struct pca953x_chip *chip;
	int ret, i;
	const struct pca953x_desc *id = NULL;

	pdata = client->dev.platform_data;
	if (pdata == NULL)
		return -ENODEV;

	/* this loop vanishes when we get i2c_device_id */
	for (i = 0; i < ARRAY_SIZE(pca953x_descs); i++)
		if (!strcmp(pca953x_descs[i].name, client->name)) {
			id = pca953x_descs + i;
			break;
		}
	if (!id)
		return -ENODEV;

	chip = kzalloc(sizeof(struct pca953x_chip), GFP_KERNEL);
	if (chip == NULL)
		return -ENOMEM;

	chip->client = client;

	chip->gpio_start = pdata->gpio_base;

	/* initialize cached registers from their original values.
	 * we can't share this chip with another i2c master.
	 */
	pca953x_setup_gpio(chip, id->driver_data);

	ret = pca953x_read_reg(chip, PCA953X_OUTPUT, &chip->reg_output);
	if (ret)
		goto out_failed;

	ret = pca953x_read_reg(chip, PCA953X_DIRECTION, &chip->reg_direction);
	if (ret)
		goto out_failed;

	/* set platform specific polarity inversion */
	ret = pca953x_write_reg(chip, PCA953X_INVERT, pdata->invert);
	if (ret)
		goto out_failed;


	ret = gpiochip_add(&chip->gpio_chip);
	if (ret)
		goto out_failed;

	if (pdata->setup) {
		ret = pdata->setup(client, chip->gpio_chip.base,
				chip->gpio_chip.ngpio, pdata->context);
		if (ret < 0)
			dev_warn(&client->dev, "setup failed, %d\n", ret);
	}

	i2c_set_clientdata(client, chip);
	return 0;

out_failed:
	kfree(chip);
	return ret;
}
Example #8
0
static int __devinit pca953x_probe(struct i2c_client *client,
				   const struct i2c_device_id *id)
{
	struct pca953x_platform_data *pdata;
	struct pca953x_chip *chip;
	int ret;

	chip = kzalloc(sizeof(struct pca953x_chip), GFP_KERNEL);
	if (chip == NULL)
		return -ENOMEM;

	pdata = client->dev.platform_data;
	if (pdata == NULL) {
		pdata = pca953x_get_alt_pdata(client);
		/*
		 * Unlike normal platform_data, this is allocated
		 * dynamically and must be freed in the driver
		 */
		chip->dyn_pdata = pdata;
	}

	if (pdata == NULL) {
		dev_dbg(&client->dev, "no platform data\n");
		ret = -EINVAL;
		goto out_failed;
	}

	chip->client = client;

	chip->gpio_start = pdata->gpio_base;

	chip->names = pdata->names;

	mutex_init(&chip->i2c_lock);

	/* initialize cached registers from their original values.
	 * we can't share this chip with another i2c master.
	 */
	pca953x_setup_gpio(chip, id->driver_data & PCA953X_GPIOS);

	ret = pca953x_read_reg(chip, PCA953X_OUTPUT, &chip->reg_output);
	if (ret)
		goto out_failed;

	ret = pca953x_read_reg(chip, PCA953X_DIRECTION, &chip->reg_direction);
	if (ret)
		goto out_failed;

	/* set platform specific polarity inversion */
	ret = pca953x_write_reg(chip, PCA953X_INVERT, pdata->invert);
	if (ret)
		goto out_failed;

	ret = pca953x_irq_setup(chip, id);
	if (ret)
		goto out_failed;

	ret = gpiochip_add(&chip->gpio_chip);
	if (ret)
		goto out_failed_irq;

	if (pdata->setup) {
		ret = pdata->setup(client, chip->gpio_chip.base,
				chip->gpio_chip.ngpio, pdata->context);
		if (ret < 0)
			dev_warn(&client->dev, "setup failed, %d\n", ret);
	}

	i2c_set_clientdata(client, chip);
	return 0;

out_failed_irq:
	pca953x_irq_teardown(chip);
out_failed:
	kfree(chip->dyn_pdata);
	kfree(chip);
	return ret;
}