Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 45ce1d23 authored by Thierry Reding's avatar Thierry Reding
Browse files

Merge branch 'for-4.11/fixes' into for-next

parents c1ae3cfa a900152b
Loading
Loading
Loading
Loading
+9 −1
Original line number Diff line number Diff line
@@ -36,6 +36,14 @@ static const struct pwm_lpss_boardinfo pwm_lpss_bxt_info = {
	.clk_rate = 19200000,
	.npwm = 4,
	.base_unit_bits = 22,
	.bypass = true,
};

/* Tangier */
static const struct pwm_lpss_boardinfo pwm_lpss_tng_info = {
	.clk_rate = 19200000,
	.npwm = 4,
	.base_unit_bits = 22,
};

static int pwm_lpss_probe_pci(struct pci_dev *pdev,
@@ -97,7 +105,7 @@ static const struct pci_device_id pwm_lpss_pci_ids[] = {
	{ PCI_VDEVICE(INTEL, 0x0ac8), (unsigned long)&pwm_lpss_bxt_info},
	{ PCI_VDEVICE(INTEL, 0x0f08), (unsigned long)&pwm_lpss_byt_info},
	{ PCI_VDEVICE(INTEL, 0x0f09), (unsigned long)&pwm_lpss_byt_info},
	{ PCI_VDEVICE(INTEL, 0x11a5), (unsigned long)&pwm_lpss_bxt_info},
	{ PCI_VDEVICE(INTEL, 0x11a5), (unsigned long)&pwm_lpss_tng_info},
	{ PCI_VDEVICE(INTEL, 0x1ac8), (unsigned long)&pwm_lpss_bxt_info},
	{ PCI_VDEVICE(INTEL, 0x2288), (unsigned long)&pwm_lpss_bsw_info},
	{ PCI_VDEVICE(INTEL, 0x2289), (unsigned long)&pwm_lpss_bsw_info},
+1 −0
Original line number Diff line number Diff line
@@ -37,6 +37,7 @@ static const struct pwm_lpss_boardinfo pwm_lpss_bxt_info = {
	.clk_rate = 19200000,
	.npwm = 4,
	.base_unit_bits = 22,
	.bypass = true,
};

static int pwm_lpss_probe_platform(struct platform_device *pdev)
+13 −6
Original line number Diff line number Diff line
@@ -57,7 +57,7 @@ static inline void pwm_lpss_write(const struct pwm_device *pwm, u32 value)
	writel(value, lpwm->regs + pwm->hwpwm * PWM_SIZE + PWM);
}

static int pwm_lpss_update(struct pwm_device *pwm)
static int pwm_lpss_wait_for_update(struct pwm_device *pwm)
{
	struct pwm_lpss_chip *lpwm = to_lpwm(pwm->chip);
	const void __iomem *addr = lpwm->regs + pwm->hwpwm * PWM_SIZE + PWM;
@@ -65,8 +65,6 @@ static int pwm_lpss_update(struct pwm_device *pwm)
	u32 val;
	int err;

	pwm_lpss_write(pwm, pwm_lpss_read(pwm) | PWM_SW_UPDATE);

	/*
	 * PWM Configuration register has SW_UPDATE bit that is set when a new
	 * configuration is written to the register. The bit is automatically
@@ -122,6 +120,12 @@ static void pwm_lpss_prepare(struct pwm_lpss_chip *lpwm, struct pwm_device *pwm,
	pwm_lpss_write(pwm, ctrl);
}

static inline void pwm_lpss_cond_enable(struct pwm_device *pwm, bool cond)
{
	if (cond)
		pwm_lpss_write(pwm, pwm_lpss_read(pwm) | PWM_ENABLE);
}

static int pwm_lpss_apply(struct pwm_chip *chip, struct pwm_device *pwm,
			  struct pwm_state *state)
{
@@ -137,18 +141,21 @@ static int pwm_lpss_apply(struct pwm_chip *chip, struct pwm_device *pwm,
				return ret;
			}
			pwm_lpss_prepare(lpwm, pwm, state->duty_cycle, state->period);
			ret = pwm_lpss_update(pwm);
			pwm_lpss_write(pwm, pwm_lpss_read(pwm) | PWM_SW_UPDATE);
			pwm_lpss_cond_enable(pwm, lpwm->info->bypass == false);
			ret = pwm_lpss_wait_for_update(pwm);
			if (ret) {
				pm_runtime_put(chip->dev);
				return ret;
			}
			pwm_lpss_write(pwm, pwm_lpss_read(pwm) | PWM_ENABLE);
			pwm_lpss_cond_enable(pwm, lpwm->info->bypass == true);
		} else {
			ret = pwm_lpss_is_updating(pwm);
			if (ret)
				return ret;
			pwm_lpss_prepare(lpwm, pwm, state->duty_cycle, state->period);
			return pwm_lpss_update(pwm);
			pwm_lpss_write(pwm, pwm_lpss_read(pwm) | PWM_SW_UPDATE);
			return pwm_lpss_wait_for_update(pwm);
		}
	} else if (pwm_is_enabled(pwm)) {
		pwm_lpss_write(pwm, pwm_lpss_read(pwm) & ~PWM_ENABLE);
+1 −0
Original line number Diff line number Diff line
@@ -22,6 +22,7 @@ struct pwm_lpss_boardinfo {
	unsigned long clk_rate;
	unsigned int npwm;
	unsigned long base_unit_bits;
	bool bypass;
};

struct pwm_lpss_chip *pwm_lpss_probe(struct device *dev, struct resource *r,
+33 −7
Original line number Diff line number Diff line
@@ -191,6 +191,28 @@ static int rockchip_pwm_config(struct pwm_chip *chip, struct pwm_device *pwm,
	return 0;
}

static int rockchip_pwm_enable(struct pwm_chip *chip,
			 struct pwm_device *pwm,
			 bool enable,
			 enum pwm_polarity polarity)
{
	struct rockchip_pwm_chip *pc = to_rockchip_pwm_chip(chip);
	int ret;

	if (enable) {
		ret = clk_enable(pc->clk);
		if (ret)
			return ret;
	}

	pc->data->set_enable(chip, pwm, enable, polarity);

	if (!enable)
		clk_disable(pc->clk);

	return 0;
}

static int rockchip_pwm_apply(struct pwm_chip *chip, struct pwm_device *pwm,
			      struct pwm_state *state)
{
@@ -207,22 +229,26 @@ static int rockchip_pwm_apply(struct pwm_chip *chip, struct pwm_device *pwm,
		return ret;

	if (state->polarity != curstate.polarity && enabled) {
		pc->data->set_enable(chip, pwm, false, state->polarity);
		ret = rockchip_pwm_enable(chip, pwm, false, state->polarity);
		if (ret)
			goto out;
		enabled = false;
	}

	ret = rockchip_pwm_config(chip, pwm, state->duty_cycle, state->period);
	if (ret) {
		if (enabled != curstate.enabled)
			pc->data->set_enable(chip, pwm, !enabled,
			rockchip_pwm_enable(chip, pwm, !enabled,
				      state->polarity);

		goto out;
	}

	if (state->enabled != enabled)
		pc->data->set_enable(chip, pwm, state->enabled,
	if (state->enabled != enabled) {
		ret = rockchip_pwm_enable(chip, pwm, state->enabled,
				    state->polarity);
		if (ret)
			goto out;
	}

	/*
	 * Update the state with the real hardware, which can differ a bit