Exemplo n.º 1
0
static irqreturn_t twl6040_naudint_handler(int irq, void *data)
{
	struct twl6040 *twl6040 = data;
	u8 intid, status;

	intid = twl6040_reg_read(twl6040, TWL6040_REG_INTID);

	if (intid & TWL6040_READYINT)
		complete(&twl6040->ready);

	if (intid & TWL6040_THINT) {
		status = twl6040_reg_read(twl6040, TWL6040_REG_STATUS);
		if (status & TWL6040_TSHUTDET) {
			dev_warn(&twl6040_dev->dev,
				 "Thermal shutdown, powering-off");
			twl6040_power(twl6040, 0);
		} else {
			dev_warn(&twl6040_dev->dev,
				 "Leaving thermal shutdown, powering-on");
			twl6040_power(twl6040, 1);
		}
	}

	return IRQ_HANDLED;
}
Exemplo n.º 2
0
static irqreturn_t twl6040_thint_handler(int irq, void *data)
{
	struct twl6040 *twl6040 = data;
	u8 status;

	status = twl6040_reg_read(twl6040, TWL6040_REG_STATUS);
	if (status & TWL6040_TSHUTDET) {
		dev_warn(twl6040->dev, "Thermal shutdown, powering-off");
		twl6040_power(twl6040, 0);
	} else {
		dev_warn(twl6040->dev, "Leaving thermal shutdown, powering-on");
		twl6040_power(twl6040, 1);
	}

	return IRQ_HANDLED;
}
Exemplo n.º 3
0
static void twl6040_vibra_enable(struct vibra_info *info)
{
	struct twl6040 *twl6040 = info->twl6040;
	int ret;

	ret = regulator_bulk_enable(ARRAY_SIZE(info->supplies), info->supplies);
	if (ret) {
		dev_err(info->dev, "failed to enable regulators %d\n", ret);
		return;
	}

	twl6040_power(info->twl6040, 1);
	if (twl6040_get_revid(twl6040) <= TWL6040_REV_ES1_1) {
		/*
		 * ERRATA: Disable overcurrent protection for at least
		 * 3ms when enabling vibrator drivers to avoid false
		 * overcurrent detection
		 */
		twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL,
				  TWL6040_VIBENA | TWL6040_VIBCTRL);
		twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR,
				  TWL6040_VIBENA | TWL6040_VIBCTRL);
		usleep_range(3000, 3500);
	}

	twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL,
			  TWL6040_VIBENA);
	twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR,
			  TWL6040_VIBENA);

	info->enabled = true;
}
static void twl6040_vibra_enable(struct vibra_info *info)
{
	struct twl6040 *twl6040 = info->twl6040;
	int ret;

	ret = regulator_bulk_enable(ARRAY_SIZE(info->supplies), info->supplies);
	if (ret) {
		dev_err(info->dev, "failed to enable regulators %d\n", ret);
		return;
	}

	twl6040_power(info->twl6040, 1);
	if (twl6040_get_revid(twl6040) <= TWL6040_REV_ES1_1) {
		/*
                                                        
                                                      
                          
   */
		twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL,
				  TWL6040_VIBENA | TWL6040_VIBCTRL);
		twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR,
				  TWL6040_VIBENA | TWL6040_VIBCTRL);
		usleep_range(3000, 3500);
	}

	twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL,
			  TWL6040_VIBENA);
	twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR,
			  TWL6040_VIBENA);

	info->enabled = true;
}
Exemplo n.º 5
0
static void omap_abe_mcpdm_shutdown(struct snd_pcm_substream *substream)
{
	struct snd_soc_pcm_runtime *rtd = substream->private_data;
	struct snd_soc_codec *codec = rtd->codec;
	struct twl6040 *twl6040 = codec->control_data;

	twl6040_power(twl6040, 0);
}
Exemplo n.º 6
0
static void omap_abe_dmic_shutdown(struct snd_pcm_substream *substream)
{
	struct snd_soc_pcm_runtime *rtd = substream->private_data;
	struct snd_soc_card *card = rtd->card;
	struct omap_abe_data *card_data = snd_soc_card_get_drvdata(card);
	struct snd_soc_codec *codec = card_data->twl6040_codec;
	struct twl6040 *twl6040 = codec->control_data;

	twl6040_power(twl6040, 0);
}
Exemplo n.º 7
0
static int omap_abe_mcpdm_startup(struct snd_pcm_substream *substream)
{
	struct snd_soc_pcm_runtime *rtd = substream->private_data;
	struct snd_soc_codec *codec = rtd->codec;
	struct snd_soc_dai *codec_dai = rtd->codec_dai;
	struct snd_soc_card *card = rtd->card;
	struct omap_abe_twl6040_data *pdata = dev_get_platdata(card->dev);
	struct twl6040 *twl6040 = codec->control_data;
	int clk_id, freq;
	int ret;

	/* twl6040 supplies McPDM PAD_CLKS */
	ret = twl6040_power(twl6040, 1);
	if (ret) {
		dev_err(card->dev, "failed to enable twl6040\n");
		return ret;
	}

	clk_id = twl6040_get_clk_id(codec);
	if (clk_id == TWL6040_SYSCLK_SEL_HPPLL)
		freq = pdata->mclk_freq;
	else if (clk_id == TWL6040_SYSCLK_SEL_LPPLL)
		freq = 32768;
	else {
		dev_err(card->dev, "invalid clock\n");
		ret = -EINVAL;
		goto err;
	}

	/* set the codec mclk */
	ret = snd_soc_dai_set_sysclk(codec_dai, clk_id, freq,
				SND_SOC_CLOCK_IN);
	if (ret) {
		dev_err(card->dev, "can't set codec system clock\n");
		goto err;
	}

	return 0;

err:
	twl6040_power(twl6040, 0);
	return ret;
}
Exemplo n.º 8
0
int twl6040_disable(struct twl6040_codec *twl6040)
{
	int ret = 0;

	mutex_lock(&twl6040->mutex);
	if (!--twl6040->power_count)
		ret = twl6040_power(twl6040, 0);
	mutex_unlock(&twl6040->mutex);

	return ret;
}
Exemplo n.º 9
0
int twl6040_enable(struct twl6040_codec *twl6040)
{
	int ret = 0;

	mutex_lock(&twl6040->mutex);
	if (!twl6040->power_count++)
		ret = twl6040_power(twl6040, 1);
	mutex_unlock(&twl6040->mutex);

	return ret;
}
Exemplo n.º 10
0
static void twl6040_vibra_disable(struct vibra_info *info)
{
	struct twl6040 *twl6040 = info->twl6040;

	twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL, 0x00);
	twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR, 0x00);
	twl6040_power(info->twl6040, 0);

	regulator_bulk_disable(ARRAY_SIZE(info->supplies), info->supplies);

	info->enabled = false;
}
int twl6040_disable(struct twl6040 *twl6040)
{
	int ret = 0;

	mutex_lock(&twl6040->mutex);
	WARN(!twl6040->power_count, "TWL6040 is already disabled");
	if (!--twl6040->power_count)
		ret = twl6040_power(twl6040, 0);
	mutex_unlock(&twl6040->mutex);

	return ret;
}
Exemplo n.º 12
0
static int twl6040_remove(struct i2c_client *client)
{
	struct twl6040 *twl6040 = i2c_get_clientdata(client);

	if (twl6040->power_count)
		twl6040_power(twl6040, 0);

	regmap_del_irq_chip(twl6040->irq, twl6040->irq_data);

	mfd_remove_devices(&client->dev);

	regulator_bulk_disable(TWL6040_NUM_SUPPLIES, twl6040->supplies);

	return 0;
}
Exemplo n.º 13
0
static int omap_abe_dmic_startup(struct snd_pcm_substream *substream)
{
	struct snd_soc_pcm_runtime *rtd = substream->private_data;
	struct snd_soc_dai *cpu_dai = rtd->cpu_dai;
	struct snd_soc_card *card = rtd->card;
	struct omap_abe_data *card_data = snd_soc_card_get_drvdata(card);
	struct snd_soc_codec *codec = card_data->twl6040_codec;
	struct twl6040 *twl6040 = codec->control_data;
	int ret = 0;

	/* twl6040 supplies DMic PAD_CLKS */
	ret = twl6040_power(twl6040, 1);
	if (ret) {
		dev_err(card->dev, "failed to enable twl6040\n");
		return ret;
	}

	ret = snd_soc_dai_set_sysclk(cpu_dai, OMAP_DMIC_SYSCLK_PAD_CLKS,
				     19200000, SND_SOC_CLOCK_IN);
	if (ret < 0) {
		dev_err(card->dev, "can't set DMIC in system clock\n");
		goto err;
	}
	ret = snd_soc_dai_set_sysclk(cpu_dai, OMAP_DMIC_ABE_DMIC_CLK, 2400000,
				     SND_SOC_CLOCK_OUT);
	if (ret < 0) {
		dev_err(card->dev, "can't set DMIC output clock\n");
		goto err;
	}

	return 0;

err:
	twl6040_power(twl6040, 0);
	return ret;
}
Exemplo n.º 14
0
static int __devexit twl6040_remove(struct platform_device *pdev)
{
	struct twl6040 *twl6040 = platform_get_drvdata(pdev);

	if (twl6040->power_count)
		twl6040_power(twl6040, 0);

	if (gpio_is_valid(twl6040->audpwron))
		gpio_free(twl6040->audpwron);

	free_irq(twl6040->irq_base + TWL6040_IRQ_READY, twl6040);
	twl6040_irq_exit(twl6040);

	mfd_remove_devices(&pdev->dev);
	platform_set_drvdata(pdev, NULL);
	kfree(twl6040);
	twl6040_dev = NULL;

	return 0;
}