Commit fcc3a5d2 authored by Linus Torvalds's avatar Linus Torvalds

Merge tag 'mfd-for-linus-3.18' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd

Pull MFD updates from Lee Jones:
 "Changes to existing drivers:
  - DT clean-ups in da9055-core, max14577, rn5t618, arizona, hi6421, stmpe, twl4030
  - Export symbols for use in modules in max14577
  - Plenty of static code analysis/Coccinelle fixes throughout the SS
  - Regmap clean-ups in arizona, wm5102, wm5110, da9052, tps65217, rk808
  - Remove unused/duplicate code in da9052, 88pm860x, ti_ssp, lpc_sch, arizona
  - Bug fixes in ti_am335x_tscadc, da9052, ti_am335x_tscadc, rtsx_pcr
  - IRQ fixups in arizona, stmpe, max14577
  - Regulator related changes in axp20x
  - Pass DMA coherency information from parent => child in MFD core
  - Rename DT document files for consistency
  - Add ACPI support to the MFD core
  - Add Andreas Werner to MAINTAINERS for MEN F21BMC

 New drivers/supported devices:
  - New driver for MEN 14F021P00 Board Management Controller
  - New driver for Ricoh RN5T618 PMIC
  - New driver for Rockchip RK808
  - New driver for HiSilicon Hi6421 PMIC
  - New driver for Qualcomm SPMI PMICs
  - Add support for Intel Braswell in lpc_ich
  - Add support for Intel 9 Series PCH in lpc_ich
  - Add support for Intel Quark ILB in lpc_sch"

[ Delayed to after the poweer/reset pull due to Kconfig problems with
  recursive Kconfig select/depends-on chains.   - Linus ]

* tag 'mfd-for-linus-3.18' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd: (79 commits)
  mfd: cros_ec: wait for completion of commands that return IN_PROGRESS
  i2c: i2c-cros-ec-tunnel: Set retries to 3
  mfd: cros_ec: move locking into cros_ec_cmd_xfer
  mfd: cros_ec: stop calling ->cmd_xfer() directly
  mfd: cros_ec: Delay for 50ms when we see EC_CMD_REBOOT_EC
  MAINTAINERS: Adds Andreas Werner to maintainers list for MEN F21BMC
  mfd: arizona: Correct mask to allow setting micbias external cap
  mfd: Add ACPI support
  Revert "mfd: wm5102: Manually apply register patch"
  mfd: ti_am335x_tscadc: Update logic in CTRL register for 5-wire TS
  mfd: dt-bindings: atmel-gpbr: Rename doc file to conform to naming convention
  mfd: dt-bindings: qcom-pm8xxx: Rename doc file to conform to naming convention
  mfd: Inherit coherent_dma_mask from parent device
  mfd: Document DT bindings for Qualcomm SPMI PMICs
  mfd: Add support for Qualcomm SPMI PMICs
  mfd: dt-bindings: pm8xxx: Add new compatible string
  mfd: axp209x: Drop the parent supplies field
  mfd: twl4030-power: Use 'ti,system-power-controller' as alternative way to support system power off
  mfd: dt-bindings: twl4030-power: Use the standard property to mark power control
  mfd: syscon: Add Atmel GPBR DT bindings documention
  ...
parents 50fa8617 d86c21fd
...@@ -312,3 +312,30 @@ a code like this: ...@@ -312,3 +312,30 @@ a code like this:
There are also devm_* versions of these functions which release the There are also devm_* versions of these functions which release the
descriptors once the device is released. descriptors once the device is released.
MFD devices
~~~~~~~~~~~
The MFD devices register their children as platform devices. For the child
devices there needs to be an ACPI handle that they can use to reference
parts of the ACPI namespace that relate to them. In the Linux MFD subsystem
we provide two ways:
o The children share the parent ACPI handle.
o The MFD cell can specify the ACPI id of the device.
For the first case, the MFD drivers do not need to do anything. The
resulting child platform device will have its ACPI_COMPANION() set to point
to the parent device.
If the ACPI namespace has a device that we can match using an ACPI id,
the id should be set like:
static struct mfd_cell my_subdevice_cell = {
.name = "my_subdevice",
/* set the resources relative to the parent */
.acpi_pnpid = "XYZ0001",
};
The ACPI id "XYZ0001" is then used to lookup an ACPI device directly under
the MFD device and if found, that ACPI companion device is bound to the
resulting child platform device.
...@@ -42,6 +42,13 @@ Optional properties: ...@@ -42,6 +42,13 @@ Optional properties:
the chip default will be used. If present exactly five values must the chip default will be used. If present exactly five values must
be specified. be specified.
- wlf,inmode : A list of INn_MODE register values, where n is the number
of input signals. Valid values are 0 (Differential), 1 (Single-ended) and
2 (Digital Microphone). If absent, INn_MODE registers set to 0 by default.
If present, values must be specified less than or equal to the number of
input singals. If values less than the number of input signals, elements
that has not been specifed are set to 0 by default.
- DCVDD-supply, MICVDD-supply : Power supplies, only need to be specified if - DCVDD-supply, MICVDD-supply : Power supplies, only need to be specified if
they are being externally supplied. As covered in they are being externally supplied. As covered in
Documentation/devicetree/bindings/regulator/regulator.txt Documentation/devicetree/bindings/regulator/regulator.txt
......
* Device tree bindings for Atmel GPBR (General Purpose Backup Registers)
The GPBR are a set of battery-backed registers.
Required properties:
- compatible: "atmel,at91sam9260-gpbr", "syscon"
- reg: contains offset/length value of the GPBR memory
region.
Example:
gpbr: gpbr@fffffd50 {
compatible = "atmel,at91sam9260-gpbr", "syscon";
reg = <0xfffffd50 0x10>;
};
* HI6421 Multi-Functional Device (MFD), by HiSilicon Ltd.
Required parent device properties:
- compatible : contains "hisilicon,hi6421-pmic";
- reg : register range space of hi6421;
Supported Hi6421 sub-devices include:
Device IRQ Names Supply Names Description
------ --------- ------------ -----------
regulators : None : None : Regulators
Required child device properties:
None.
Example:
hi6421 {
compatible = "hisilicon,hi6421-pmic";
reg = <0xfcc00000 0x0180>; /* 0x60 << 2 */
regulators {
// supply for MLC NAND/ eMMC
hi6421_vout0_reg: hi6421_vout0 {
regulator-name = "VOUT0";
regulator-min-microvolt = <2850000>;
regulator-max-microvolt = <2850000>;
};
// supply for 26M Oscillator
hi6421_vout1_reg: hi6421_vout1 {
regulator-name = "VOUT1";
regulator-min-microvolt = <1700000>;
regulator-max-microvolt = <2000000>;
regulator-boot-on;
regulator-always-on;
};
};
};
Qualcomm SPMI PMICs multi-function device bindings
The Qualcomm SPMI series presently includes PM8941, PM8841 and PMA8084
PMICs. These PMICs use a QPNP scheme through SPMI interface.
QPNP is effectively a partitioning scheme for dividing the SPMI extended
register space up into logical pieces, and set of fixed register
locations/definitions within these regions, with some of these regions
specifically used for interrupt handling.
The QPNP PMICs are used with the Qualcomm Snapdragon series SoCs, and are
interfaced to the chip via the SPMI (System Power Management Interface) bus.
Support for multiple independent functions are implemented by splitting the
16-bit SPMI slave address space into 256 smaller fixed-size regions, 256 bytes
each. A function can consume one or more of these fixed-size register regions.
Required properties:
- compatible: Should contain one of:
"qcom,pm8941"
"qcom,pm8841"
"qcom,pma8084"
or generalized "qcom,spmi-pmic".
- reg: Specifies the SPMI USID slave address for this device.
For more information see:
Documentation/devicetree/bindings/spmi/spmi.txt
Required properties for peripheral child nodes:
- compatible: Should contain "qcom,xxx", where "xxx" is a peripheral name.
Optional properties for peripheral child nodes:
- interrupts: Interrupts are specified as a 4-tuple. For more information
see:
Documentation/devicetree/bindings/spmi/qcom,spmi-pmic-arb.txt
- interrupt-names: Corresponding interrupt name to the interrupts property
Each child node of SPMI slave id represents a function of the PMIC. In the
example below the rtc device node represents a peripheral of pm8941
SID = 0. The regulator device node represents a peripheral of pm8941 SID = 1.
Example:
spmi {
compatible = "qcom,spmi-pmic-arb";
pm8941@0 {
compatible = "qcom,pm8941", "qcom,spmi-pmic";
reg = <0x0 SPMI_USID>;
rtc {
compatible = "qcom,rtc";
interrupts = <0x0 0x61 0x1 IRQ_TYPE_EDGE_RISING>;
interrupt-names = "alarm";
};
};
pm8941@1 {
compatible = "qcom,pm8941", "qcom,spmi-pmic";
reg = <0x1 SPMI_USID>;
regulator {
compatible = "qcom,regulator";
regulator-name = "8941_boost";
};
};
};
...@@ -61,6 +61,7 @@ The below bindings specify the set of valid subnodes. ...@@ -61,6 +61,7 @@ The below bindings specify the set of valid subnodes.
Definition: must be one of: Definition: must be one of:
"qcom,pm8058-rtc" "qcom,pm8058-rtc"
"qcom,pm8921-rtc" "qcom,pm8921-rtc"
"qcom,pm8941-rtc"
- reg: - reg:
Usage: required Usage: required
......
RK808 Power Management Integrated Circuit
Required properties:
- compatible: "rockchip,rk808"
- reg: I2C slave address
- interrupt-parent: The parent interrupt controller.
- interrupts: the interrupt outputs of the controller.
- #clock-cells: from common clock binding; shall be set to 1 (multiple clock
outputs). See <dt-bindings/clock/rockchip,rk808.h> for clock IDs.
Optional properties:
- clock-output-names: From common clock binding to override the
default output clock name
- rockchip,system-power-controller: Telling whether or not this pmic is controlling
the system power.
- vcc1-supply: The input supply for DCDC_REG1
- vcc2-supply: The input supply for DCDC_REG2
- vcc3-supply: The input supply for DCDC_REG3
- vcc4-supply: The input supply for DCDC_REG4
- vcc6-supply: The input supply for LDO_REG1 and LDO_REG2
- vcc7-supply: The input supply for LDO_REG3 and LDO_REG7
- vcc8-supply: The input supply for SWITCH_REG1
- vcc9-supply: The input supply for LDO_REG4 and LDO_REG5
- vcc10-supply: The input supply for LDO_REG6
- vcc11-supply: The input supply for LDO_REG8
- vcc12-supply: The input supply for SWITCH_REG2
Regulators: All the regulators of RK808 to be instantiated shall be
listed in a child node named 'regulators'. Each regulator is represented
by a child node of the 'regulators' node.
regulator-name {
/* standard regulator bindings here */
};
Following regulators of the RK808 PMIC block are supported. Note that
the 'n' in regulator name, as in DCDC_REGn or LDOn, represents the DCDC or LDO
number as described in RK808 datasheet.
- DCDC_REGn
- valid values for n are 1 to 4.
- LDO_REGn
- valid values for n are 1 to 8.
- SWITCH_REGn
- valid values for n are 1 to 2
Standard regulator bindings are used inside regulator subnodes. Check
Documentation/devicetree/bindings/regulator/regulator.txt
for more details
Example:
rk808: pmic@1b {
compatible = "rockchip,rk808";
clock-output-names = "xin32k", "rk808-clkout2";
interrupt-parent = <&gpio0>;
interrupts = <4 IRQ_TYPE_LEVEL_LOW>;
pinctrl-names = "default";
pinctrl-0 = <&pmic_int>;
reg = <0x1b>;
rockchip,system-power-controller;
wakeup-source;
#clock-cells = <1>;
vcc8-supply = <&vcc_18>;
vcc9-supply = <&vcc_io>;
vcc10-supply = <&vcc_io>;
vcc12-supply = <&vcc_io>;
vddio-supply = <&vccio_pmu>;
regulators {
vdd_cpu: DCDC_REG1 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <750000>;
regulator-max-microvolt = <1300000>;
regulator-name = "vdd_arm";
};
vdd_gpu: DCDC_REG2 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <850000>;
regulator-max-microvolt = <1250000>;
regulator-name = "vdd_gpu";
};
vcc_ddr: DCDC_REG3 {
regulator-always-on;
regulator-boot-on;
regulator-name = "vcc_ddr";
};
vcc_io: DCDC_REG4 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <3300000>;
regulator-max-microvolt = <3300000>;
regulator-name = "vcc_io";
};
vccio_pmu: LDO_REG1 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <3300000>;
regulator-max-microvolt = <3300000>;
regulator-name = "vccio_pmu";
};
vcc_tp: LDO_REG2 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <3300000>;
regulator-max-microvolt = <3300000>;
regulator-name = "vcc_tp";
};
vdd_10: LDO_REG3 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <1000000>;
regulator-max-microvolt = <1000000>;
regulator-name = "vdd_10";
};
vcc18_lcd: LDO_REG4 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <1800000>;
regulator-max-microvolt = <1800000>;
regulator-name = "vcc18_lcd";
};
vccio_sd: LDO_REG5 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <1800000>;
regulator-max-microvolt = <3300000>;
regulator-name = "vccio_sd";
};
vdd10_lcd: LDO_REG6 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <1000000>;
regulator-max-microvolt = <1000000>;
regulator-name = "vdd10_lcd";
};
vcc_18: LDO_REG7 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <1800000>;
regulator-max-microvolt = <1800000>;
regulator-name = "vcc_18";
};
vcca_codec: LDO_REG8 {
regulator-always-on;
regulator-boot-on;
regulator-min-microvolt = <3300000>;
regulator-max-microvolt = <3300000>;
regulator-name = "vcca_codec";
};
vcc_wl: SWITCH_REG1 {
regulator-always-on;
regulator-boot-on;
regulator-name = "vcc_wl";
};
vcc_lcd: SWITCH_REG2 {
regulator-always-on;
regulator-boot-on;
regulator-name = "vcc_lcd";
};
};
};
* Ricoh RN5T618 PMIC
Ricoh RN5T618 is a power management IC which integrates 3 step-down
DCDC converters, 7 low-dropout regulators, a Li-ion battery charger,
fuel gauge, ADC, GPIOs and a watchdog timer. It can be controlled
through a I2C interface.
Required properties:
- compatible: should be "ricoh,rn5t618"
- reg: the I2C slave address of the device
Sub-nodes:
- regulators: the node is required if the regulator functionality is
needed. The valid regulator names are: DCDC1, DCDC2, DCDC3, LDO1,
LDO2, LDO3, LDO4, LDO5, LDORTC1 and LDORTC2.
The common bindings for each individual regulator can be found in:
Documentation/devicetree/bindings/regulator/regulator.txt
Example:
pmic@32 {
compatible = "ricoh,rn5t618";
reg = <0x32>;
regulators {
DCDC1 {
regulator-min-microvolt = <1050000>;
regulator-max-microvolt = <1050000>;
};
DCDC2 {
regulator-min-microvolt = <1175000>;
regulator-max-microvolt = <1175000>;
};
};
};
...@@ -13,6 +13,7 @@ Optional properties: ...@@ -13,6 +13,7 @@ Optional properties:
- interrupt-parent : Specifies which IRQ controller we're connected to - interrupt-parent : Specifies which IRQ controller we're connected to
- wakeup-source : Marks the input device as wakable - wakeup-source : Marks the input device as wakable
- st,autosleep-timeout : Valid entries (ms); 4, 16, 32, 64, 128, 256, 512 and 1024 - st,autosleep-timeout : Valid entries (ms); 4, 16, 32, 64, 128, 256, 512 and 1024
- irq-gpio : If present, which GPIO to use for event IRQ
Example: Example:
......
...@@ -23,8 +23,13 @@ down during off-idle. Note that this does not work on all boards ...@@ -23,8 +23,13 @@ down during off-idle. Note that this does not work on all boards
depending on how the external oscillator is wired. depending on how the external oscillator is wired.
Optional properties: Optional properties:
- ti,use_poweroff: With this flag, the chip will initiates an ACTIVE-to-OFF or
SLEEP-to-OFF transition when the system poweroffs. - ti,system-power-controller: This indicates that TWL4030 is the
power supply master of the system. With this flag, the chip will
initiate an ACTIVE-to-OFF or SLEEP-to-OFF transition when the
system poweroffs.
- ti,use_poweroff: Deprecated name for ti,system-power-controller
Example: Example:
&i2c1 { &i2c1 {
......
...@@ -6010,6 +6010,15 @@ S: Supported ...@@ -6010,6 +6010,15 @@ S: Supported
F: drivers/mcb/ F: drivers/mcb/
F: include/linux/mcb.h F: include/linux/mcb.h
MEN F21BMC (Board Management Controller)
M: Andreas Werner <andreas.werner@men.de>
S: Supported
F: drivers/mfd/menf21bmc.c
F: drivers/watchdog/menf21bmc_wdt.c
F: drivers/leds/leds-menf21bmc.c
F: drivers/hwmon/menf21bmc_hwmon.c
F: Documentation/hwmon/menf21bmc
METAG ARCHITECTURE METAG ARCHITECTURE
M: James Hogan <james.hogan@imgtec.com> M: James Hogan <james.hogan@imgtec.com>
L: linux-metag@vger.kernel.org L: linux-metag@vger.kernel.org
......
...@@ -16,6 +16,8 @@ ...@@ -16,6 +16,8 @@
#include <linux/platform_device.h> #include <linux/platform_device.h>
#include <linux/slab.h> #include <linux/slab.h>
#define I2C_MAX_RETRIES 3
/** /**
* struct ec_i2c_device - Driver data for I2C tunnel * struct ec_i2c_device - Driver data for I2C tunnel
* *
...@@ -227,7 +229,7 @@ static int ec_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg i2c_msgs[], ...@@ -227,7 +229,7 @@ static int ec_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg i2c_msgs[],
msg.indata = response; msg.indata = response;
msg.insize = response_len; msg.insize = response_len;
result = bus->ec->cmd_xfer(bus->ec, &msg); result = cros_ec_cmd_xfer(bus->ec, &msg);
if (result < 0) if (result < 0)
goto exit; goto exit;
...@@ -290,6 +292,7 @@ static int ec_i2c_probe(struct platform_device *pdev) ...@@ -290,6 +292,7 @@ static int ec_i2c_probe(struct platform_device *pdev)
bus->adap.algo_data = bus; bus->adap.algo_data = bus;
bus->adap.dev.parent = &pdev->dev; bus->adap.dev.parent = &pdev->dev;
bus->adap.dev.of_node = np; bus->adap.dev.of_node = np;
bus->adap.retries = I2C_MAX_RETRIES;
err = i2c_add_adapter(&bus->adap); err = i2c_add_adapter(&bus->adap);
if (err) { if (err) {
......
...@@ -157,7 +157,7 @@ static int cros_ec_keyb_get_state(struct cros_ec_keyb *ckdev, uint8_t *kb_state) ...@@ -157,7 +157,7 @@ static int cros_ec_keyb_get_state(struct cros_ec_keyb *ckdev, uint8_t *kb_state)
.insize = ckdev->cols, .insize = ckdev->cols,
}; };
return ckdev->ec->cmd_xfer(ckdev->ec, &msg); return cros_ec_cmd_xfer(ckdev->ec, &msg);
} }
static irqreturn_t cros_ec_keyb_irq(int irq, void *data) static irqreturn_t cros_ec_keyb_irq(int irq, void *data)
......
...@@ -122,7 +122,7 @@ static int read_device(struct i2c_client *i2c, int reg, ...@@ -122,7 +122,7 @@ static int read_device(struct i2c_client *i2c, int reg,
static int write_device(struct i2c_client *i2c, int reg, static int write_device(struct i2c_client *i2c, int reg,
int bytes, void *src) int bytes, void *src)
{ {
unsigned char buf[bytes + 1]; unsigned char buf[2];
struct i2c_adapter *adap = i2c->adapter; struct i2c_adapter *adap = i2c->adapter;
struct i2c_msg msg; struct i2c_msg msg;
int ret; int ret;
...@@ -140,26 +140,6 @@ static int write_device(struct i2c_client *i2c, int reg, ...@@ -140,26 +140,6 @@ static int write_device(struct i2c_client *i2c, int reg,
return 0; return 0;
} }
int pm860x_page_reg_read(struct i2c_client *i2c, int reg)
{
unsigned char zero = 0;
unsigned char data;
int ret;
i2c_lock_adapter(i2c->adapter);
read_device(i2c, 0xFA, 0, &zero);
read_device(i2c, 0xFB, 0, &zero);
read_device(i2c, 0xFF, 0, &zero);
ret = read_device(i2c, reg, 1, &data);
if (ret >= 0)
ret = (int)data;
read_device(i2c, 0xFE, 0, &zero);
read_device(i2c, 0xFC, 0, &zero);
i2c_unlock_adapter(i2c->adapter);
return ret;
}
EXPORT_SYMBOL(pm860x_page_reg_read);
int pm860x_page_reg_write(struct i2c_client *i2c, int reg, int pm860x_page_reg_write(struct i2c_client *i2c, int reg,
unsigned char data) unsigned char data)
{ {
...@@ -195,47 +175,3 @@ int pm860x_page_bulk_read(struct i2c_client *i2c, int reg, ...@@ -195,47 +175,3 @@ int pm860x_page_bulk_read(struct i2c_client *i2c, int reg,
return ret; return ret;
} }
EXPORT_SYMBOL(pm860x_page_bulk_read); EXPORT_SYMBOL(pm860x_page_bulk_read);
int pm860x_page_bulk_write(struct i2c_client *i2c, int reg,
int count, unsigned char *buf)
{
unsigned char zero = 0;
int ret;
i2c_lock_adapter(i2c->adapter);
read_device(i2c, 0xFA, 0, &zero);
read_device(i2c, 0xFB, 0, &zero);
read_device(i2c, 0xFF, 0, &zero);
ret = write_device(i2c, reg, count, buf);
read_device(i2c, 0xFE, 0, &zero);
read_device(i2c, 0xFC, 0, &zero);
i2c_unlock_adapter(i2c->adapter);
i2c_unlock_adapter(i2c->adapter);
return ret;
}
EXPORT_SYMBOL(pm860x_page_bulk_write);
int pm860x_page_set_bits(struct i2c_client *i2c, int reg,
unsigned char mask, unsigned char data)
{
unsigned char zero;
unsigned char value;
int ret;
i2c_lock_adapter(i2c->adapter);
read_device(i2c, 0xFA, 0, &zero);
read_device(i2c, 0xFB, 0, &zero);
read_device(i2c, 0xFF, 0, &zero);
ret = read_device(i2c, reg, 1, &value);
if (ret < 0)
goto out;
value &= ~mask;
value |= data;
ret = write_device(i2c, reg, 1, &value);
out:
read_device(i2c, 0xFE, 0, &zero);
read_device(i2c, 0xFC, 0, &zero);
i2c_unlock_adapter(i2c->adapter);
return ret;
}
EXPORT_SYMBOL(pm860x_page_set_bits);
...@@ -210,6 +210,19 @@ config MFD_MC13XXX_I2C ...@@ -210,6 +210,19 @@ config MFD_MC13XXX_I2C
help help
Select this if your MC13xxx is connected via an I2C bus. Select this if your MC13xxx is connected via an I2C bus.
config MFD_HI6421_PMIC
tristate "HiSilicon Hi6421 PMU/Codec IC"
depends on OF
select MFD_CORE
select REGMAP_MMIO
help
Add support for HiSilicon Hi6421 PMIC. Hi6421 includes multi-
functions, such as regulators, RTC, codec, Coulomb counter, etc.
This driver includes core APIs _only_. You have to select
individul components like voltage regulators under corresponding
menus in order to enable them.
We communicate with the Hi6421 via memory-mapped I/O.
config HTC_EGPIO config HTC_EGPIO
bool "HTC EGPIO support" bool "HTC EGPIO support"
depends on GPIOLIB && ARM depends on GPIOLIB && ARM
...@@ -554,6 +567,21 @@ config MFD_PM8921_CORE ...@@ -554,6 +567,21 @@ config MFD_PM8921_CORE
Say M here if you want to include support for PM8921 chip as a module. Say M here if you want to include support for PM8921 chip as a module.
This will build a module called "pm8921-core". This will build a module called "pm8921-core".
config MFD_SPMI_PMIC
tristate "Qualcomm SPMI PMICs"
depends on ARCH_QCOM || COMPILE_TEST
depends on OF
depends on SPMI
select REGMAP_SPMI
help
This enables support for the Qualcomm SPMI PMICs.
These PMICs are currently used with the Snapdragon 800 series of
SoCs. Note, that this will only be useful paired with descriptions
of the independent functions as children nodes in the device tree.
Say M here if you want to include support for the SPMI PMIC
series as a module. The module will be called "qcom-spmi-pmic".
config MFD_RDC321X config MFD_RDC321X
tristate "RDC R-321x southbridge" tristate "RDC R-321x southbridge"
select MFD_CORE select MFD_CORE
...@@ -597,6 +625,30 @@ config MFD_RC5T583 ...@@ -597,6 +625,30 @@ config MFD_RC5T583
Additional drivers must be enabled in order to use the Additional drivers must be enabled in order to use the
different functionality of the device. different functionality of the device.
config MFD_RK808
tristate "Rockchip RK808 Power Management chip"
depends on I2C && OF
select MFD_CORE
select REGMAP_I2C
select REGMAP_IRQ
help
If you say yes here you get support for the RK808
Power Management chips.
This driver provides common support for accessing the device
through I2C interface. The device supports multiple sub-devices
including interrupts, RTC, LDO & DCDC regulators, and onkey.
config MFD_RN5T618
tristate "Ricoh RN5T5618 PMIC"
depends on I2C
select MFD_CORE
select REGMAP_I2C
help
Say yes here to add support for the Ricoh RN5T618 PMIC. This
driver provides common support for accessing the device,
additional drivers must be enabled in order to use the
functionality of the device.
config MFD_SEC_CORE config MFD_SEC_CORE
bool "SAMSUNG Electronics PMIC Series Support" bool "SAMSUNG Electronics PMIC Series Support"
depends on I2C=y depends on I2C=y
...@@ -1243,11 +1295,11 @@ config MFD_WM8350_I2C ...@@ -1243,11 +1295,11 @@ config MFD_WM8350_I2C
selected to enable support for the functionality of the chip. selected to enable support for the functionality of the chip.
config MFD_WM8994 config MFD_WM8994
bool "Wolfson Microelectronics WM8994" tristate "Wolfson Microelectronics WM8994"
select MFD_CORE select MFD_CORE
select REGMAP_I2C select REGMAP_I2C
select REGMAP_IRQ select REGMAP_IRQ
depends on I2C=y depends on I2C
help help
The WM8994 is a highly integrated hi-fi CODEC designed for The WM8994 is a highly integrated hi-fi CODEC designed for
smartphone applicatiosn. As well as audio functionality it smartphone applicatiosn. As well as audio functionality it
......
...@@ -153,6 +153,7 @@ obj-$(CONFIG_MFD_SI476X_CORE) += si476x-core.o ...@@ -153,6 +153,7 @@ obj-$(CONFIG_MFD_SI476X_CORE) += si476x-core.o
obj-$(CONFIG_MFD_CS5535) += cs5535-mfd.o obj-$(CONFIG_MFD_CS5535) += cs5535-mfd.o
obj-$(CONFIG_MFD_OMAP_USB_HOST) += omap-usb-host.o omap-usb-tll.o obj-$(CONFIG_MFD_OMAP_USB_HOST) += omap-usb-host.o omap-usb-tll.o
obj-$(CONFIG_MFD_PM8921_CORE) += pm8921-core.o ssbi.o obj-$(CONFIG_MFD_PM8921_CORE) += pm8921-core.o ssbi.o
obj-$(CONFIG_MFD_SPMI_PMIC) += qcom-spmi-pmic.o
obj-$(CONFIG_TPS65911_COMPARATOR) += tps65911-comparator.o obj-$(CONFIG_TPS65911_COMPARATOR) += tps65911-comparator.o
obj-$(CONFIG_MFD_TPS65090) += tps65090.o obj-$(CONFIG_MFD_TPS65090) += tps65090.o
obj-$(CONFIG_MFD_AAT2870_CORE) += aat2870-core.o obj-$(CONFIG_MFD_AAT2870_CORE) += aat2870-core.o
...@@ -160,6 +161,8 @@ obj-$(CONFIG_MFD_INTEL_MSIC) += intel_msic.o ...@@ -160,6 +161,8 @@ obj-$(CONFIG_MFD_INTEL_MSIC) += intel_msic.o
obj-$(CONFIG_MFD_PALMAS) += palmas.o obj-$(CONFIG_MFD_PALMAS) += palmas.o
obj-$(CONFIG_MFD_VIPERBOARD) += viperboard.o obj-$(CONFIG_MFD_VIPERBOARD) += viperboard.o
obj-$(CONFIG_MFD_RC5T583) += rc5t583.o rc5t583-irq.o obj-$(CONFIG_MFD_RC5T583) += rc5t583.o rc5t583-irq.o
obj-$(CONFIG_MFD_RK808) += rk808.o
obj-$(CONFIG_MFD_RN5T618) += rn5t618.o
obj-$(CONFIG_MFD_SEC_CORE) += sec-core.o sec-irq.o obj-$(CONFIG_MFD_SEC_CORE) += sec-core.o sec-irq.o
obj-$(CONFIG_MFD_SYSCON) += syscon.o obj-$(CONFIG_MFD_SYSCON) += syscon.o
obj-$(CONFIG_MFD_LM3533) += lm3533-core.o lm3533-ctrlbank.o obj-$(CONFIG_MFD_LM3533) += lm3533-core.o lm3533-ctrlbank.o
...@@ -170,6 +173,7 @@ obj-$(CONFIG_MFD_AS3722) += as3722.o ...@@ -170,6 +173,7 @@ obj-$(CONFIG_MFD_AS3722) += as3722.o
obj-$(CONFIG_MFD_STW481X) += stw481x.o obj-$(CONFIG_MFD_STW481X) += stw481x.o
obj-$(CONFIG_MFD_IPAQ_MICRO) += ipaq-micro.o obj-$(CONFIG_MFD_IPAQ_MICRO) += ipaq-micro.o
obj-$(CONFIG_MFD_MENF21BMC) += menf21bmc.o obj-$(CONFIG_MFD_MENF21BMC) += menf21bmc.o
obj-$(CONFIG_MFD_HI6421_PMIC) += hi6421-pmic-core.o
intel-soc-pmic-objs := intel_soc_pmic_core.o intel_soc_pmic_crc.o intel-soc-pmic-objs := intel_soc_pmic_core.o intel_soc_pmic_crc.o
obj-$(CONFIG_INTEL_SOC_PMIC) += intel-soc-pmic.o obj-$(CONFIG_INTEL_SOC_PMIC) += intel-soc-pmic.o
...@@ -393,18 +393,6 @@ static int arizona_runtime_resume(struct device *dev) ...@@ -393,18 +393,6 @@ static int arizona_runtime_resume(struct device *dev)
break; break;
} }
switch (arizona->type) {
case WM5102:
ret = wm5102_patch(arizona);
if (ret != 0) {
dev_err(arizona->dev, "Failed to apply patch: %d\n",
ret);
goto err;
}
default:
break;
}
ret = regcache_sync(arizona->regmap); ret = regcache_sync(arizona->regmap);
if (ret != 0) { if (ret != 0) {
dev_err(arizona->dev, "Failed to restore register cache\n"); dev_err(arizona->dev, "Failed to restore register cache\n");
...@@ -534,7 +522,11 @@ EXPORT_SYMBOL_GPL(arizona_of_get_named_gpio); ...@@ -534,7 +522,11 @@ EXPORT_SYMBOL_GPL(arizona_of_get_named_gpio);
static int arizona_of_get_core_pdata(struct arizona *arizona) static int arizona_of_get_core_pdata(struct arizona *arizona)
{ {
struct arizona_pdata *pdata = &arizona->pdata; struct arizona_pdata *pdata = &arizona->pdata;
struct property *prop;
const __be32 *cur;
u32 val;
int ret, i; int ret, i;
int count = 0;
pdata->reset = arizona_of_get_named_gpio(arizona, "wlf,reset", true); pdata->reset = arizona_of_get_named_gpio(arizona, "wlf,reset", true);
...@@ -560,6 +552,15 @@ static int arizona_of_get_core_pdata(struct arizona *arizona) ...@@ -560,6 +552,15 @@ static int arizona_of_get_core_pdata(struct arizona *arizona)
ret); ret);
} }
of_property_for_each_u32(arizona->dev->of_node, "wlf,inmode", prop,
cur, val) {
if (count == ARRAY_SIZE(arizona->pdata.inmode))
break;
arizona->pdata.inmode[count] = val;
count++;
}
return 0; return 0;
} }
...@@ -784,7 +785,8 @@ int arizona_dev_init(struct arizona *arizona) ...@@ -784,7 +785,8 @@ int arizona_dev_init(struct arizona *arizona)
/* Ensure device startup is complete */ /* Ensure device startup is complete */
switch (arizona->type) { switch (arizona->type) {
case WM5102: case WM5102:
ret = regmap_read(arizona->regmap, 0x19, &val); ret = regmap_read(arizona->regmap,
ARIZONA_WRITE_SEQUENCER_CTRL_3, &val);
if (ret != 0) if (ret != 0)
dev_err(dev, dev_err(dev,
"Failed to check write sequencer state: %d\n", "Failed to check write sequencer state: %d\n",
...@@ -945,6 +947,7 @@ int arizona_dev_init(struct arizona *arizona) ...@@ -945,6 +947,7 @@ int arizona_dev_init(struct arizona *arizona)
regmap_update_bits(arizona->regmap, regmap_update_bits(arizona->regmap,
ARIZONA_MIC_BIAS_CTRL_1 + i, ARIZONA_MIC_BIAS_CTRL_1 + i,
ARIZONA_MICB1_LVL_MASK | ARIZONA_MICB1_LVL_MASK |
ARIZONA_MICB1_EXT_CAP |
ARIZONA_MICB1_DISCH | ARIZONA_MICB1_DISCH |
ARIZONA_MICB1_BYPASS | ARIZONA_MICB1_BYPASS |
ARIZONA_MICB1_RATE, val); ARIZONA_MICB1_RATE, val);
......
...@@ -152,10 +152,18 @@ static void arizona_irq_disable(struct irq_data *data) ...@@ -152,10 +152,18 @@ static void arizona_irq_disable(struct irq_data *data)
{ {
} }
static int arizona_irq_set_wake(struct irq_data *data, unsigned int on)
{
struct arizona *arizona = irq_data_get_irq_chip_data(data);
return irq_set_irq_wake(arizona->irq, on);
}
static struct irq_chip arizona_irq_chip = { static struct irq_chip arizona_irq_chip = {
.name = "arizona", .name = "arizona",
.irq_disable = arizona_irq_disable, .irq_disable = arizona_irq_disable,
.irq_enable = arizona_irq_enable, .irq_enable = arizona_irq_enable,
.irq_set_wake = arizona_irq_set_wake,
}; };
static int arizona_irq_map(struct irq_domain *h, unsigned int virq, static int arizona_irq_map(struct irq_domain *h, unsigned int virq,
...@@ -164,7 +172,7 @@ static int arizona_irq_map(struct irq_domain *h, unsigned int virq, ...@@ -164,7 +172,7 @@ static int arizona_irq_map(struct irq_domain *h, unsigned int virq,
struct regmap_irq_chip_data *data = h->host_data; struct regmap_irq_chip_data *data = h->host_data;
irq_set_chip_data(virq, data); irq_set_chip_data(virq, data);
irq_set_chip_and_handler(virq, &arizona_irq_chip, handle_edge_irq); irq_set_chip_and_handler(virq, &arizona_irq_chip, handle_simple_irq);
irq_set_nested_thread(virq, 1); irq_set_nested_thread(virq, 1);
/* ARM needs us to explicitly flag the IRQ as valid /* ARM needs us to explicitly flag the IRQ as valid
...@@ -282,7 +290,7 @@ int arizona_irq_init(struct arizona *arizona) ...@@ -282,7 +290,7 @@ int arizona_irq_init(struct arizona *arizona)
ret = regmap_add_irq_chip(arizona->regmap, ret = regmap_add_irq_chip(arizona->regmap,
irq_create_mapping(arizona->virq, 0), irq_create_mapping(arizona->virq, 0),
IRQF_ONESHOT, -1, aod, IRQF_ONESHOT, 0, aod,
&arizona->aod_irq_chip); &arizona->aod_irq_chip);
if (ret != 0) { if (ret != 0) {
dev_err(arizona->dev, "Failed to add AOD IRQs: %d\n", ret); dev_err(arizona->dev, "Failed to add AOD IRQs: %d\n", ret);
...@@ -291,7 +299,7 @@ int arizona_irq_init(struct arizona *arizona) ...@@ -291,7 +299,7 @@ int arizona_irq_init(struct arizona *arizona)
ret = regmap_add_irq_chip(arizona->regmap, ret = regmap_add_irq_chip(arizona->regmap,
irq_create_mapping(arizona->virq, 1), irq_create_mapping(arizona->virq, 1),
IRQF_ONESHOT, -1, irq, IRQF_ONESHOT, 0, irq,
&arizona->irq_chip); &arizona->irq_chip);
if (ret != 0) { if (ret != 0) {
dev_err(arizona->dev, "Failed to add main IRQs: %d\n", ret); dev_err(arizona->dev, "Failed to add main IRQs: %d\n", ret);
......
...@@ -140,15 +140,6 @@ static const struct regmap_irq_chip axp20x_regmap_irq_chip = { ...@@ -140,15 +140,6 @@ static const struct regmap_irq_chip axp20x_regmap_irq_chip = {
.init_ack_masked = true, .init_ack_masked = true,
}; };
static const char * const axp20x_supplies[] = {
"acin",
"vin2",
"vin3",
"ldo24in",
"ldo3in",
"ldo5in",
};
static struct mfd_cell axp20x_cells[] = { static struct mfd_cell axp20x_cells[] = {
{ {
.name = "axp20x-pek", .name = "axp20x-pek",
...@@ -156,8 +147,6 @@ static struct mfd_cell axp20x_cells[] = { ...@@ -156,8 +147,6 @@ static struct mfd_cell axp20x_cells[] = {
.resources = axp20x_pek_resources, .resources = axp20x_pek_resources,
}, { }, {
.name = "axp20x-regulator", .name = "axp20x-regulator",
.parent_supplies = axp20x_supplies,
.num_parent_supplies = ARRAY_SIZE(axp20x_supplies),
}, },
}; };
......
...@@ -23,6 +23,9 @@ ...@@ -23,6 +23,9 @@
#include <linux/mfd/core.h> #include <linux/mfd/core.h>
#include <linux/mfd/cros_ec.h> #include <linux/mfd/cros_ec.h>
#include <linux/mfd/cros_ec_commands.h> #include <linux/mfd/cros_ec_commands.h>
#include <linux/delay.h>
#define EC_COMMAND_RETRIES 50
int cros_ec_prepare_tx(struct cros_ec_device *ec_dev, int cros_ec_prepare_tx(struct cros_ec_device *ec_dev,
struct cros_ec_command *msg) struct cros_ec_command *msg)
...@@ -62,6 +65,49 @@ int cros_ec_check_result(struct cros_ec_device *ec_dev, ...@@ -62,6 +65,49 @@ int cros_ec_check_result(struct cros_ec_device *ec_dev,
} }
EXPORT_SYMBOL(cros_ec_check_result); EXPORT_SYMBOL(cros_ec_check_result);
int cros_ec_cmd_xfer(struct cros_ec_device *ec_dev,
struct cros_ec_command *msg)
{
int ret;
mutex_lock(&ec_dev->lock);
ret = ec_dev->cmd_xfer(ec_dev, msg);
if (msg->result == EC_RES_IN_PROGRESS) {
int i;
struct cros_ec_command status_msg;
struct ec_response_get_comms_status status;
status_msg.version = 0;
status_msg.command = EC_CMD_GET_COMMS_STATUS;
status_msg.outdata = NULL;
status_msg.outsize = 0;
status_msg.indata = (uint8_t *)&status;
status_msg.insize = sizeof(status);
/*
* Query the EC's status until it's no longer busy or
* we encounter an error.
*/
for (i = 0; i < EC_COMMAND_RETRIES; i++) {
usleep_range(10000, 11000);
ret = ec_dev->cmd_xfer(ec_dev, &status_msg);
if (ret < 0)
break;
msg->result = status_msg.result;
if (status_msg.result != EC_RES_SUCCESS)
break;
if (!(status.flags & EC_COMMS_STATUS_PROCESSING))
break;
}
}
mutex_unlock(&ec_dev->lock);
return ret;
}
EXPORT_SYMBOL(cros_ec_cmd_xfer);
static const struct mfd_cell cros_devs[] = { static const struct mfd_cell cros_devs[] = {
{ {
.name = "cros-ec-keyb", .name = "cros-ec-keyb",
...@@ -91,6 +137,8 @@ int cros_ec_register(struct cros_ec_device *ec_dev) ...@@ -91,6 +137,8 @@ int cros_ec_register(struct cros_ec_device *ec_dev)
return -ENOMEM; return -ENOMEM;
} }
mutex_init(&ec_dev->lock);
err = mfd_add_devices(dev, 0, cros_devs, err = mfd_add_devices(dev, 0, cros_devs,
ARRAY_SIZE(cros_devs), ARRAY_SIZE(cros_devs),
NULL, ec_dev->irq, NULL); NULL, ec_dev->irq, NULL);
......
...@@ -65,6 +65,12 @@ ...@@ -65,6 +65,12 @@
*/ */
#define EC_SPI_RECOVERY_TIME_NS (200 * 1000) #define EC_SPI_RECOVERY_TIME_NS (200 * 1000)
/*
* The EC is unresponsive for a time after a reboot command. Add a
* simple delay to make sure that the bus stays locked.
*/
#define EC_REBOOT_DELAY_MS 50
/** /**
* struct cros_ec_spi - information about a SPI-connected EC * struct cros_ec_spi - information about a SPI-connected EC
* *
...@@ -73,13 +79,11 @@ ...@@ -73,13 +79,11 @@
* if no record * if no record
* @end_of_msg_delay: used to set the delay_usecs on the spi_transfer that * @end_of_msg_delay: used to set the delay_usecs on the spi_transfer that
* is sent when we want to turn off CS at the end of a transaction. * is sent when we want to turn off CS at the end of a transaction.
* @lock: mutex to ensure only one user of cros_ec_cmd_xfer_spi at a time
*/ */
struct cros_ec_spi { struct cros_ec_spi {
struct spi_device *spi; struct spi_device *spi;
s64 last_transfer_ns; s64 last_transfer_ns;
unsigned int end_of_msg_delay; unsigned int end_of_msg_delay;
struct mutex lock;
}; };
static void debug_packet(struct device *dev, const char *name, u8 *ptr, static void debug_packet(struct device *dev, const char *name, u8 *ptr,
...@@ -226,13 +230,6 @@ static int cros_ec_cmd_xfer_spi(struct cros_ec_device *ec_dev, ...@@ -226,13 +230,6 @@ static int cros_ec_cmd_xfer_spi(struct cros_ec_device *ec_dev,
int sum; int sum;
int ret = 0, final_ret; int ret = 0, final_ret;
/*
* We have the shared ec_dev buffer plus we do lots of separate spi_sync
* calls, so we need to make sure only one person is using this at a
* time.
*/
mutex_lock(&ec_spi->lock);
len = cros_ec_prepare_tx(ec_dev, ec_msg); len = cros_ec_prepare_tx(ec_dev, ec_msg);
dev_dbg(ec_dev->dev, "prepared, len=%d\n", len); dev_dbg(ec_dev->dev, "prepared, len=%d\n", len);
...@@ -318,7 +315,9 @@ static int cros_ec_cmd_xfer_spi(struct cros_ec_device *ec_dev, ...@@ -318,7 +315,9 @@ static int cros_ec_cmd_xfer_spi(struct cros_ec_device *ec_dev,
ret = len; ret = len;
exit: exit:
mutex_unlock(&ec_spi->lock); if (ec_msg->command == EC_CMD_REBOOT_EC)
msleep(EC_REBOOT_DELAY_MS);
return ret; return ret;
} }
...@@ -350,7 +349,6 @@ static int cros_ec_spi_probe(struct spi_device *spi) ...@@ -350,7 +349,6 @@ static int cros_ec_spi_probe(struct spi_device *spi)
if (ec_spi == NULL) if (ec_spi == NULL)
return -ENOMEM; return -ENOMEM;
ec_spi->spi = spi; ec_spi->spi = spi;
mutex_init(&ec_spi->lock);
ec_dev = devm_kzalloc(dev, sizeof(*ec_dev), GFP_KERNEL); ec_dev = devm_kzalloc(dev, sizeof(*ec_dev), GFP_KERNEL);
if (!ec_dev) if (!ec_dev)
return -ENOMEM; return -ENOMEM;
......
...@@ -522,7 +522,7 @@ static const struct mfd_cell da9052_subdev_info[] = { ...@@ -522,7 +522,7 @@ static const struct mfd_cell da9052_subdev_info[] = {
}, },
}; };
struct regmap_config da9052_regmap_config = { const struct regmap_config da9052_regmap_config = {
.reg_bits = 8, .reg_bits = 8,
.val_bits = 8, .val_bits = 8,
......
...@@ -140,13 +140,6 @@ static int da9052_i2c_probe(struct i2c_client *client, ...@@ -140,13 +140,6 @@ static int da9052_i2c_probe(struct i2c_client *client,
if (!da9052) if (!da9052)
return -ENOMEM; return -ENOMEM;
if (!i2c_check_functionality(client->adapter,
I2C_FUNC_SMBUS_BYTE_DATA)) {
dev_info(&client->dev, "Error in %s:i2c_check_functionality\n",
__func__);
return -ENODEV;
}
da9052->dev = &client->dev; da9052->dev = &client->dev;
da9052->chip_irq = client->irq; da9052->chip_irq = client->irq;
da9052->fix_io = da9052_i2c_fix; da9052->fix_io = da9052_i2c_fix;
......
...@@ -23,6 +23,7 @@ ...@@ -23,6 +23,7 @@
static int da9052_spi_probe(struct spi_device *spi) static int da9052_spi_probe(struct spi_device *spi)
{ {
struct regmap_config config;
int ret; int ret;
const struct spi_device_id *id = spi_get_device_id(spi); const struct spi_device_id *id = spi_get_device_id(spi);
struct da9052 *da9052; struct da9052 *da9052;
...@@ -40,10 +41,10 @@ static int da9052_spi_probe(struct spi_device *spi) ...@@ -40,10 +41,10 @@ static int da9052_spi_probe(struct spi_device *spi)
spi_set_drvdata(spi, da9052); spi_set_drvdata(spi, da9052);
da9052_regmap_config.read_flag_mask = 1; config = da9052_regmap_config;
da9052_regmap_config.write_flag_mask = 0; config.read_flag_mask = 1;
da9052->regmap = devm_regmap_init_spi(spi, &da9052_regmap_config); da9052->regmap = devm_regmap_init_spi(spi, &config);
if (IS_ERR(da9052->regmap)) { if (IS_ERR(da9052->regmap)) {
ret = PTR_ERR(da9052->regmap); ret = PTR_ERR(da9052->regmap);
dev_err(&spi->dev, "Failed to allocate register map: %d\n", dev_err(&spi->dev, "Failed to allocate register map: %d\n",
......
/*
* Device driver for Hi6421 IC
*
* Copyright (c) <2011-2014> HiSilicon Technologies Co., Ltd.
* http://www.hisilicon.com
* Copyright (c) <2013-2014> Linaro Ltd.
* http://www.linaro.org
*
* Author: Guodong Xu <guodong.xu@linaro.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <linux/device.h>
#include <linux/err.h>
#include <linux/mfd/core.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/platform_device.h>
#include <linux/regmap.h>
#include <linux/mfd/hi6421-pmic.h>
static const struct mfd_cell hi6421_devs[] = {
{ .name = "hi6421-regulator", },
};
static struct regmap_config hi6421_regmap_config = {
.reg_bits = 32,
.reg_stride = 4,
.val_bits = 8,
.max_register = HI6421_REG_TO_BUS_ADDR(HI6421_REG_MAX),
};
static int hi6421_pmic_probe(struct platform_device *pdev)
{
struct hi6421_pmic *pmic;
struct resource *res;
void __iomem *base;
int ret;
pmic = devm_kzalloc(&pdev->dev, sizeof(*pmic), GFP_KERNEL);
if (!pmic)
return -ENOMEM;
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
base = devm_ioremap_resource(&pdev->dev, res);
if (IS_ERR(base))
return PTR_ERR(base);
pmic->regmap = devm_regmap_init_mmio_clk(&pdev->dev, NULL, base,
&hi6421_regmap_config);
if (IS_ERR(pmic->regmap)) {
dev_err(&pdev->dev,
"regmap init failed: %ld\n", PTR_ERR(pmic->regmap));
return PTR_ERR(pmic->regmap);
}
/* set over-current protection debounce 8ms */
regmap_update_bits(pmic->regmap, HI6421_OCP_DEB_CTRL_REG,
(HI6421_OCP_DEB_SEL_MASK
| HI6421_OCP_EN_DEBOUNCE_MASK
| HI6421_OCP_AUTO_STOP_MASK),
(HI6421_OCP_DEB_SEL_8MS
| HI6421_OCP_EN_DEBOUNCE_ENABLE));
platform_set_drvdata(pdev, pmic);
ret = mfd_add_devices(&pdev->dev, 0, hi6421_devs,
ARRAY_SIZE(hi6421_devs), NULL, 0, NULL);
if (ret) {
dev_err(&pdev->dev, "add mfd devices failed: %d\n", ret);
return ret;
}
return 0;
}
static int hi6421_pmic_remove(struct platform_device *pdev)
{
mfd_remove_devices(&pdev->dev);
return 0;
}
static struct of_device_id of_hi6421_pmic_match_tbl[] = {
{ .compatible = "hisilicon,hi6421-pmic", },
{ },
};
static struct platform_driver hi6421_pmic_driver = {
.driver = {
.name = "hi6421_pmic",
.of_match_table = of_hi6421_pmic_match_tbl,
},
.probe = hi6421_pmic_probe,
.remove = hi6421_pmic_remove,
};
module_platform_driver(hi6421_pmic_driver);
MODULE_AUTHOR("Guodong Xu <guodong.xu@linaro.org>");
MODULE_DESCRIPTION("Hi6421 PMIC driver");
MODULE_LICENSE("GPL v2");
...@@ -227,15 +227,12 @@ static irqreturn_t htcpld_handler(int irq, void *dev) ...@@ -227,15 +227,12 @@ static irqreturn_t htcpld_handler(int irq, void *dev)
static void htcpld_chip_set(struct gpio_chip *chip, unsigned offset, int val) static void htcpld_chip_set(struct gpio_chip *chip, unsigned offset, int val)
{ {
struct i2c_client *client; struct i2c_client *client;
struct htcpld_chip *chip_data; struct htcpld_chip *chip_data =
container_of(chip, struct htcpld_chip, chip_out);
unsigned long flags; unsigned long flags;
chip_data = container_of(chip, struct htcpld_chip, chip_out);
if (!chip_data)
return;
client = chip_data->client; client = chip_data->client;
if (client == NULL) if (!client)
return; return;
spin_lock_irqsave(&chip_data->lock, flags); spin_lock_irqsave(&chip_data->lock, flags);
...@@ -261,31 +258,18 @@ static void htcpld_chip_set_ni(struct work_struct *work) ...@@ -261,31 +258,18 @@ static void htcpld_chip_set_ni(struct work_struct *work)
static int htcpld_chip_get(struct gpio_chip *chip, unsigned offset) static int htcpld_chip_get(struct gpio_chip *chip, unsigned offset)
{ {
struct htcpld_chip *chip_data; struct htcpld_chip *chip_data;
int val = 0; u8 cache;
int is_input = 0;
/* Try out first */ if (!strncmp(chip->label, "htcpld-out", 10)) {
chip_data = container_of(chip, struct htcpld_chip, chip_out); chip_data = container_of(chip, struct htcpld_chip, chip_out);
if (!chip_data) { cache = chip_data->cache_out;
/* Try in */ } else if (!strncmp(chip->label, "htcpld-in", 9)) {
is_input = 1;
chip_data = container_of(chip, struct htcpld_chip, chip_in); chip_data = container_of(chip, struct htcpld_chip, chip_in);
if (!chip_data) cache = chip_data->cache_in;
} else
return -EINVAL; return -EINVAL;
}
/* Determine if this is an input or output GPIO */
if (!is_input)
/* Use the output cache */
val = (chip_data->cache_out >> offset) & 1;
else
/* Use the input cache */
val = (chip_data->cache_in >> offset) & 1;
if (val) return (cache >> offset) & 1;
return 1;
else
return 0;
} }
static int htcpld_direction_output(struct gpio_chip *chip, static int htcpld_direction_output(struct gpio_chip *chip,
...@@ -376,7 +360,7 @@ static int htcpld_register_chip_i2c( ...@@ -376,7 +360,7 @@ static int htcpld_register_chip_i2c(
plat_chip_data = &pdata->chip[chip_index]; plat_chip_data = &pdata->chip[chip_index];
adapter = i2c_get_adapter(pdata->i2c_adapter_id); adapter = i2c_get_adapter(pdata->i2c_adapter_id);
if (adapter == NULL) { if (!adapter) {
/* Eek, no such I2C adapter! Bail out. */ /* Eek, no such I2C adapter! Bail out. */
dev_warn(dev, "Chip at i2c address 0x%x: Invalid i2c adapter %d\n", dev_warn(dev, "Chip at i2c address 0x%x: Invalid i2c adapter %d\n",
plat_chip_data->addr, pdata->i2c_adapter_id); plat_chip_data->addr, pdata->i2c_adapter_id);
......
...@@ -115,6 +115,7 @@ static void intel_soc_pmic_shutdown(struct i2c_client *i2c) ...@@ -115,6 +115,7 @@ static void intel_soc_pmic_shutdown(struct i2c_client *i2c)
return; return;
} }
#if defined(CONFIG_PM_SLEEP)
static int intel_soc_pmic_suspend(struct device *dev) static int intel_soc_pmic_suspend(struct device *dev)
{ {
struct intel_soc_pmic *pmic = dev_get_drvdata(dev); struct intel_soc_pmic *pmic = dev_get_drvdata(dev);
...@@ -132,6 +133,7 @@ static int intel_soc_pmic_resume(struct device *dev) ...@@ -132,6 +133,7 @@ static int intel_soc_pmic_resume(struct device *dev)
return 0; return 0;
} }
#endif
static SIMPLE_DEV_PM_OPS(intel_soc_pmic_pm_ops, intel_soc_pmic_suspend, static SIMPLE_DEV_PM_OPS(intel_soc_pmic_pm_ops, intel_soc_pmic_suspend,
intel_soc_pmic_resume); intel_soc_pmic_resume);
......
...@@ -54,6 +54,7 @@ ...@@ -54,6 +54,7 @@
* document number TBD : Avoton SoC * document number TBD : Avoton SoC
* document number TBD : Coleto Creek * document number TBD : Coleto Creek
* document number TBD : Wildcat Point-LP * document number TBD : Wildcat Point-LP
* document number TBD : 9 Series
*/ */
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
...@@ -216,6 +217,8 @@ enum lpc_chipsets { ...@@ -216,6 +217,8 @@ enum lpc_chipsets {
LPC_BAYTRAIL, /* Bay Trail SoC */ LPC_BAYTRAIL, /* Bay Trail SoC */
LPC_COLETO, /* Coleto Creek */ LPC_COLETO, /* Coleto Creek */
LPC_WPT_LP, /* Wildcat Point-LP */ LPC_WPT_LP, /* Wildcat Point-LP */
LPC_BRASWELL, /* Braswell SoC */
LPC_9S, /* 9 Series */
}; };
static struct lpc_ich_info lpc_chipset_info[] = { static struct lpc_ich_info lpc_chipset_info[] = {
...@@ -519,6 +522,14 @@ static struct lpc_ich_info lpc_chipset_info[] = { ...@@ -519,6 +522,14 @@ static struct lpc_ich_info lpc_chipset_info[] = {
.name = "Wildcat Point_LP", .name = "Wildcat Point_LP",
.iTCO_version = 2, .iTCO_version = 2,
}, },
[LPC_BRASWELL] = {
.name = "Braswell SoC",
.iTCO_version = 3,
},
[LPC_9S] = {
.name = "9 Series",
.iTCO_version = 2,
},
}; };
/* /*
...@@ -745,6 +756,12 @@ static const struct pci_device_id lpc_ich_ids[] = { ...@@ -745,6 +756,12 @@ static const struct pci_device_id lpc_ich_ids[] = {
{ PCI_VDEVICE(INTEL, 0x9cc6), LPC_WPT_LP}, { PCI_VDEVICE(INTEL, 0x9cc6), LPC_WPT_LP},
{ PCI_VDEVICE(INTEL, 0x9cc7), LPC_WPT_LP}, { PCI_VDEVICE(INTEL, 0x9cc7), LPC_WPT_LP},
{ PCI_VDEVICE(INTEL, 0x9cc9), LPC_WPT_LP}, { PCI_VDEVICE(INTEL, 0x9cc9), LPC_WPT_LP},
{ PCI_VDEVICE(INTEL, 0x229c), LPC_BRASWELL},
{ PCI_VDEVICE(INTEL, 0x8cc1), LPC_9S},
{ PCI_VDEVICE(INTEL, 0x8cc2), LPC_9S},
{ PCI_VDEVICE(INTEL, 0x8cc3), LPC_9S},
{ PCI_VDEVICE(INTEL, 0x8cc4), LPC_9S},
{ PCI_VDEVICE(INTEL, 0x8cc6), LPC_9S},
{ 0, }, /* End of list */ { 0, }, /* End of list */
}; };
MODULE_DEVICE_TABLE(pci, lpc_ich_ids); MODULE_DEVICE_TABLE(pci, lpc_ich_ids);
......
...@@ -7,6 +7,7 @@ ...@@ -7,6 +7,7 @@
* Configuration Registers. * Configuration Registers.
* *
* Copyright (c) 2010 CompuLab Ltd * Copyright (c) 2010 CompuLab Ltd
* Copyright (c) 2014 Intel Corp.
* Author: Denis Turischev <denis@compulab.co.il> * Author: Denis Turischev <denis@compulab.co.il>
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
...@@ -17,10 +18,6 @@ ...@@ -17,10 +18,6 @@
* but WITHOUT ANY WARRANTY; without even the implied warranty of * but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details. * GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*/ */
#include <linux/kernel.h> #include <linux/kernel.h>
...@@ -37,123 +34,165 @@ ...@@ -37,123 +34,165 @@
#define GPIO_IO_SIZE 64 #define GPIO_IO_SIZE 64
#define GPIO_IO_SIZE_CENTERTON 128 #define GPIO_IO_SIZE_CENTERTON 128
/* Intel Quark X1000 GPIO IRQ Number */
#define GPIO_IRQ_QUARK_X1000 9
#define WDTBASE 0x84 #define WDTBASE 0x84
#define WDT_IO_SIZE 64 #define WDT_IO_SIZE 64
static struct resource smbus_sch_resource = { enum sch_chipsets {
.flags = IORESOURCE_IO, LPC_SCH = 0, /* Intel Poulsbo SCH */
}; LPC_ITC, /* Intel Tunnel Creek */
LPC_CENTERTON, /* Intel Centerton */
static struct resource gpio_sch_resource = { LPC_QUARK_X1000, /* Intel Quark X1000 */
.flags = IORESOURCE_IO,
}; };
static struct resource wdt_sch_resource = { struct lpc_sch_info {
.flags = IORESOURCE_IO, unsigned int io_size_smbus;
}; unsigned int io_size_gpio;
unsigned int io_size_wdt;
static struct mfd_cell lpc_sch_cells[3]; int irq_gpio;
static struct mfd_cell isch_smbus_cell = {
.name = "isch_smbus",
.num_resources = 1,
.resources = &smbus_sch_resource,
.ignore_resource_conflicts = true,
}; };
static struct mfd_cell sch_gpio_cell = { static struct lpc_sch_info sch_chipset_info[] = {
.name = "sch_gpio", [LPC_SCH] = {
.num_resources = 1, .io_size_smbus = SMBUS_IO_SIZE,
.resources = &gpio_sch_resource, .io_size_gpio = GPIO_IO_SIZE,
.ignore_resource_conflicts = true, .irq_gpio = -1,
}; },
[LPC_ITC] = {
static struct mfd_cell wdt_sch_cell = { .io_size_smbus = SMBUS_IO_SIZE,
.name = "ie6xx_wdt", .io_size_gpio = GPIO_IO_SIZE,
.num_resources = 1, .io_size_wdt = WDT_IO_SIZE,
.resources = &wdt_sch_resource, .irq_gpio = -1,
.ignore_resource_conflicts = true, },
[LPC_CENTERTON] = {
.io_size_smbus = SMBUS_IO_SIZE,
.io_size_gpio = GPIO_IO_SIZE_CENTERTON,
.io_size_wdt = WDT_IO_SIZE,
.irq_gpio = -1,
},
[LPC_QUARK_X1000] = {
.io_size_gpio = GPIO_IO_SIZE,
.irq_gpio = GPIO_IRQ_QUARK_X1000,
},
}; };
static const struct pci_device_id lpc_sch_ids[] = { static const struct pci_device_id lpc_sch_ids[] = {
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_SCH_LPC) }, { PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_SCH_LPC), LPC_SCH },
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ITC_LPC) }, { PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_ITC_LPC), LPC_ITC },
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_CENTERTON_ILB) }, { PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_CENTERTON_ILB), LPC_CENTERTON },
{ PCI_VDEVICE(INTEL, PCI_DEVICE_ID_INTEL_QUARK_X1000_ILB), LPC_QUARK_X1000 },
{ 0, } { 0, }
}; };
MODULE_DEVICE_TABLE(pci, lpc_sch_ids); MODULE_DEVICE_TABLE(pci, lpc_sch_ids);
static int lpc_sch_probe(struct pci_dev *dev, #define LPC_NO_RESOURCE 1
const struct pci_device_id *id) #define LPC_SKIP_RESOURCE 2
static int lpc_sch_get_io(struct pci_dev *pdev, int where, const char *name,
struct resource *res, int size)
{ {
unsigned int base_addr_cfg; unsigned int base_addr_cfg;
unsigned short base_addr; unsigned short base_addr;
int i, cells = 0;
int ret;
pci_read_config_dword(dev, SMBASE, &base_addr_cfg); if (size == 0)
return LPC_NO_RESOURCE;
pci_read_config_dword(pdev, where, &base_addr_cfg);
base_addr = 0; base_addr = 0;
if (!(base_addr_cfg & (1 << 31))) if (!(base_addr_cfg & (1 << 31)))
dev_warn(&dev->dev, "Decode of the SMBus I/O range disabled\n"); dev_warn(&pdev->dev, "Decode of the %s I/O range disabled\n",
name);
else else
base_addr = (unsigned short)base_addr_cfg; base_addr = (unsigned short)base_addr_cfg;
if (base_addr == 0) { if (base_addr == 0) {
dev_warn(&dev->dev, "I/O space for SMBus uninitialized\n"); dev_warn(&pdev->dev, "I/O space for %s uninitialized\n", name);
} else { return LPC_SKIP_RESOURCE;
lpc_sch_cells[cells++] = isch_smbus_cell;
smbus_sch_resource.start = base_addr;
smbus_sch_resource.end = base_addr + SMBUS_IO_SIZE - 1;
} }
pci_read_config_dword(dev, GPIOBASE, &base_addr_cfg); res->start = base_addr;
base_addr = 0; res->end = base_addr + size - 1;
if (!(base_addr_cfg & (1 << 31))) res->flags = IORESOURCE_IO;
dev_warn(&dev->dev, "Decode of the GPIO I/O range disabled\n");
else
base_addr = (unsigned short)base_addr_cfg;
if (base_addr == 0) { return 0;
dev_warn(&dev->dev, "I/O space for GPIO uninitialized\n"); }
} else {
lpc_sch_cells[cells++] = sch_gpio_cell;
gpio_sch_resource.start = base_addr;
if (id->device == PCI_DEVICE_ID_INTEL_CENTERTON_ILB)
gpio_sch_resource.end = base_addr + GPIO_IO_SIZE_CENTERTON - 1;
else
gpio_sch_resource.end = base_addr + GPIO_IO_SIZE - 1;
}
if (id->device == PCI_DEVICE_ID_INTEL_ITC_LPC static int lpc_sch_populate_cell(struct pci_dev *pdev, int where,
|| id->device == PCI_DEVICE_ID_INTEL_CENTERTON_ILB) { const char *name, int size, int irq,
pci_read_config_dword(dev, WDTBASE, &base_addr_cfg); int id, struct mfd_cell *cell)
base_addr = 0; {
if (!(base_addr_cfg & (1 << 31))) struct resource *res;
dev_warn(&dev->dev, "Decode of the WDT I/O range disabled\n"); int ret;
else
base_addr = (unsigned short)base_addr_cfg;
if (base_addr == 0)
dev_warn(&dev->dev, "I/O space for WDT uninitialized\n");
else {
lpc_sch_cells[cells++] = wdt_sch_cell;
wdt_sch_resource.start = base_addr;
wdt_sch_resource.end = base_addr + WDT_IO_SIZE - 1;
}
}
if (WARN_ON(cells > ARRAY_SIZE(lpc_sch_cells))) { res = devm_kcalloc(&pdev->dev, 2, sizeof(*res), GFP_KERNEL);
dev_err(&dev->dev, "Cell count exceeds array size"); if (!res)
return -ENODEV; return -ENOMEM;
}
ret = lpc_sch_get_io(pdev, where, name, res, size);
if (ret)
return ret;
memset(cell, 0, sizeof(*cell));
cell->name = name;
cell->resources = res;
cell->num_resources = 1;
cell->ignore_resource_conflicts = true;
cell->id = id;
/* Check if we need to add an IRQ resource */
if (irq < 0)
return 0;
res++;
res->start = irq;
res->end = irq;
res->flags = IORESOURCE_IRQ;
cell->num_resources++;
return 0;
}
static int lpc_sch_probe(struct pci_dev *dev, const struct pci_device_id *id)
{
struct mfd_cell lpc_sch_cells[3];
struct lpc_sch_info *info = &sch_chipset_info[id->driver_data];
unsigned int cells = 0;
int ret;
ret = lpc_sch_populate_cell(dev, SMBASE, "isch_smbus",
info->io_size_smbus, -1,
id->device, &lpc_sch_cells[cells]);
if (ret < 0)
return ret;
if (ret == 0)
cells++;
ret = lpc_sch_populate_cell(dev, GPIOBASE, "sch_gpio",
info->io_size_gpio, info->irq_gpio,
id->device, &lpc_sch_cells[cells]);
if (ret < 0)
return ret;
if (ret == 0)
cells++;
ret = lpc_sch_populate_cell(dev, WDTBASE, "ie6xx_wdt",
info->io_size_wdt, -1,
id->device, &lpc_sch_cells[cells]);
if (ret < 0)
return ret;
if (ret == 0)
cells++;
if (cells == 0) { if (cells == 0) {
dev_err(&dev->dev, "All decode registers disabled.\n"); dev_err(&dev->dev, "All decode registers disabled.\n");
return -ENODEV; return -ENODEV;
} }
for (i = 0; i < cells; i++)
lpc_sch_cells[i].id = id->device;
ret = mfd_add_devices(&dev->dev, 0, lpc_sch_cells, cells, NULL, 0, NULL); ret = mfd_add_devices(&dev->dev, 0, lpc_sch_cells, cells, NULL, 0, NULL);
if (ret) if (ret)
mfd_remove_devices(&dev->dev); mfd_remove_devices(&dev->dev);
......
...@@ -456,8 +456,7 @@ static int max14577_i2c_probe(struct i2c_client *i2c, ...@@ -456,8 +456,7 @@ static int max14577_i2c_probe(struct i2c_client *i2c,
} }
ret = mfd_add_devices(max14577->dev, -1, mfd_devs, ret = mfd_add_devices(max14577->dev, -1, mfd_devs,
mfd_devs_size, NULL, 0, mfd_devs_size, NULL, 0, NULL);
regmap_irq_get_domain(max14577->irq_data));
if (ret < 0) if (ret < 0)
goto err_mfd; goto err_mfd;
......
...@@ -52,7 +52,7 @@ static const struct mfd_cell max77802_devs[] = { ...@@ -52,7 +52,7 @@ static const struct mfd_cell max77802_devs[] = {
static bool max77802_pmic_is_accessible_reg(struct device *dev, static bool max77802_pmic_is_accessible_reg(struct device *dev,
unsigned int reg) unsigned int reg)
{ {
return (reg >= MAX77802_REG_DEVICE_ID && reg < MAX77802_REG_PMIC_END); return reg < MAX77802_REG_PMIC_END;
} }
static bool max77802_rtc_is_accessible_reg(struct device *dev, static bool max77802_rtc_is_accessible_reg(struct device *dev,
......
...@@ -44,9 +44,12 @@ ...@@ -44,9 +44,12 @@
static const struct mfd_cell max77693_devs[] = { static const struct mfd_cell max77693_devs[] = {
{ .name = "max77693-pmic", }, { .name = "max77693-pmic", },
{ .name = "max77693-charger", }, { .name = "max77693-charger", },
{ .name = "max77693-flash", },
{ .name = "max77693-muic", }, { .name = "max77693-muic", },
{ .name = "max77693-haptic", }, { .name = "max77693-haptic", },
{
.name = "max77693-flash",
.of_compatible = "maxim,max77693-flash",
},
}; };
static const struct regmap_config max77693_regmap_config = { static const struct regmap_config max77693_regmap_config = {
......
...@@ -37,7 +37,7 @@ static inline int max8925_read_device(struct i2c_client *i2c, ...@@ -37,7 +37,7 @@ static inline int max8925_read_device(struct i2c_client *i2c,
static inline int max8925_write_device(struct i2c_client *i2c, static inline int max8925_write_device(struct i2c_client *i2c,
int reg, int bytes, void *src) int reg, int bytes, void *src)
{ {
unsigned char buf[bytes + 1]; unsigned char buf[9];
int ret; int ret;
buf[0] = (unsigned char)reg; buf[0] = (unsigned char)reg;
......
...@@ -36,6 +36,9 @@ ...@@ -36,6 +36,9 @@
#define MC34708_REVISION_FIN (0x07 << 6) #define MC34708_REVISION_FIN (0x07 << 6)
#define MC34708_REVISION_FAB (0x07 << 9) #define MC34708_REVISION_FAB (0x07 << 9)
#define MC13XXX_PWRCTRL 15
#define MC13XXX_PWRCTRL_WDIRESET (1 << 12)
#define MC13XXX_ADC1 44 #define MC13XXX_ADC1 44
#define MC13XXX_ADC1_ADEN (1 << 0) #define MC13XXX_ADC1_ADEN (1 << 0)
#define MC13XXX_ADC1_RAND (1 << 1) #define MC13XXX_ADC1_RAND (1 << 1)
...@@ -416,6 +419,11 @@ int mc13xxx_common_init(struct device *dev) ...@@ -416,6 +419,11 @@ int mc13xxx_common_init(struct device *dev)
mc13xxx->variant->print_revision(mc13xxx, revision); mc13xxx->variant->print_revision(mc13xxx, revision);
ret = mc13xxx_reg_rmw(mc13xxx, MC13XXX_PWRCTRL,
MC13XXX_PWRCTRL_WDIRESET, MC13XXX_PWRCTRL_WDIRESET);
if (ret)
return ret;
for (i = 0; i < ARRAY_SIZE(mc13xxx->irqs); i++) { for (i = 0; i < ARRAY_SIZE(mc13xxx->irqs); i++) {
mc13xxx->irqs[i].reg_offset = i / MC13XXX_IRQ_PER_REG; mc13xxx->irqs[i].reg_offset = i / MC13XXX_IRQ_PER_REG;
mc13xxx->irqs[i].mask = BIT(i % MC13XXX_IRQ_PER_REG); mc13xxx->irqs[i].mask = BIT(i % MC13XXX_IRQ_PER_REG);
......
...@@ -466,8 +466,6 @@ static int menelaus_set_voltage(const struct menelaus_vtg *vtg, int mV, ...@@ -466,8 +466,6 @@ static int menelaus_set_voltage(const struct menelaus_vtg *vtg, int mV,
struct i2c_client *c = the_menelaus->client; struct i2c_client *c = the_menelaus->client;
mutex_lock(&the_menelaus->lock); mutex_lock(&the_menelaus->lock);
if (!vtg)
goto set_voltage;
ret = menelaus_read_reg(vtg->vtg_reg); ret = menelaus_read_reg(vtg->vtg_reg);
if (ret < 0) if (ret < 0)
...@@ -482,7 +480,6 @@ static int menelaus_set_voltage(const struct menelaus_vtg *vtg, int mV, ...@@ -482,7 +480,6 @@ static int menelaus_set_voltage(const struct menelaus_vtg *vtg, int mV,
ret = menelaus_write_reg(vtg->vtg_reg, val); ret = menelaus_write_reg(vtg->vtg_reg, val);
if (ret < 0) if (ret < 0)
goto out; goto out;
set_voltage:
ret = menelaus_write_reg(vtg->mode_reg, mode); ret = menelaus_write_reg(vtg->mode_reg, mode);
out: out:
mutex_unlock(&the_menelaus->lock); mutex_unlock(&the_menelaus->lock);
...@@ -1186,7 +1183,7 @@ static int menelaus_probe(struct i2c_client *client, ...@@ -1186,7 +1183,7 @@ static int menelaus_probe(struct i2c_client *client,
const struct i2c_device_id *id) const struct i2c_device_id *id)
{ {
struct menelaus_chip *menelaus; struct menelaus_chip *menelaus;
int rev = 0, val; int rev = 0;
int err = 0; int err = 0;
struct menelaus_platform_data *menelaus_pdata = struct menelaus_platform_data *menelaus_pdata =
dev_get_platdata(&client->dev); dev_get_platdata(&client->dev);
...@@ -1239,10 +1236,10 @@ static int menelaus_probe(struct i2c_client *client, ...@@ -1239,10 +1236,10 @@ static int menelaus_probe(struct i2c_client *client,
pr_info("Menelaus rev %d.%d\n", rev >> 4, rev & 0x0f); pr_info("Menelaus rev %d.%d\n", rev >> 4, rev & 0x0f);
val = menelaus_read_reg(MENELAUS_VCORE_CTRL1); err = menelaus_read_reg(MENELAUS_VCORE_CTRL1);
if (val < 0) if (err < 0)
goto fail; goto fail;
if (val & (1 << 7)) if (err & BIT(7))
menelaus->vcore_hw_mode = 1; menelaus->vcore_hw_mode = 1;
else else
menelaus->vcore_hw_mode = 0; menelaus->vcore_hw_mode = 0;
......
...@@ -78,6 +78,44 @@ static int mfd_platform_add_cell(struct platform_device *pdev, ...@@ -78,6 +78,44 @@ static int mfd_platform_add_cell(struct platform_device *pdev,
return 0; return 0;
} }
#if IS_ENABLED(CONFIG_ACPI)
static void mfd_acpi_add_device(const struct mfd_cell *cell,
struct platform_device *pdev)
{
struct acpi_device *parent_adev;
struct acpi_device *adev;
parent_adev = ACPI_COMPANION(pdev->dev.parent);
if (!parent_adev)
return;
/*
* MFD child device gets its ACPI handle either from the ACPI
* device directly under the parent that matches the acpi_pnpid or
* it will use the parent handle if is no acpi_pnpid is given.
*/
adev = parent_adev;
if (cell->acpi_pnpid) {
struct acpi_device_id ids[2] = {};
struct acpi_device *child_adev;
strlcpy(ids[0].id, cell->acpi_pnpid, sizeof(ids[0].id));
list_for_each_entry(child_adev, &parent_adev->children, node)
if (acpi_match_device_ids(child_adev, ids)) {
adev = child_adev;
break;
}
}
ACPI_COMPANION_SET(&pdev->dev, adev);
}
#else
static inline void mfd_acpi_add_device(const struct mfd_cell *cell,
struct platform_device *pdev)
{
}
#endif
static int mfd_add_device(struct device *parent, int id, static int mfd_add_device(struct device *parent, int id,
const struct mfd_cell *cell, atomic_t *usage_count, const struct mfd_cell *cell, atomic_t *usage_count,
struct resource *mem_base, struct resource *mem_base,
...@@ -101,6 +139,7 @@ static int mfd_add_device(struct device *parent, int id, ...@@ -101,6 +139,7 @@ static int mfd_add_device(struct device *parent, int id,
pdev->dev.type = &mfd_dev_type; pdev->dev.type = &mfd_dev_type;
pdev->dev.dma_mask = parent->dma_mask; pdev->dev.dma_mask = parent->dma_mask;
pdev->dev.dma_parms = parent->dma_parms; pdev->dev.dma_parms = parent->dma_parms;
pdev->dev.coherent_dma_mask = parent->coherent_dma_mask;
ret = regulator_bulk_register_supply_alias( ret = regulator_bulk_register_supply_alias(
&pdev->dev, cell->parent_supplies, &pdev->dev, cell->parent_supplies,
...@@ -118,6 +157,8 @@ static int mfd_add_device(struct device *parent, int id, ...@@ -118,6 +157,8 @@ static int mfd_add_device(struct device *parent, int id,
} }
} }
mfd_acpi_add_device(cell, pdev);
if (cell->pdata_size) { if (cell->pdata_size) {
ret = platform_device_add_data(pdev, ret = platform_device_add_data(pdev,
cell->platform_data, cell->pdata_size); cell->platform_data, cell->pdata_size);
......
...@@ -106,10 +106,7 @@ static ssize_t show_dump_regs(struct device *dev, struct device_attribute *attr, ...@@ -106,10 +106,7 @@ static ssize_t show_dump_regs(struct device *dev, struct device_attribute *attr,
} else } else
dump[n1] = pcf50633_reg_read(pcf, n + n1); dump[n1] = pcf50633_reg_read(pcf, n + n1);
hex_dump_to_buffer(dump, sizeof(dump), 16, 1, buf1, 128, 0); buf1 += sprintf(buf1, "%*ph\n", (int)sizeof(dump), dump);
buf1 += strlen(buf1);
*buf1++ = '\n';
*buf1 = '\0';
} }
return buf1 - buf; return buf1 - buf;
...@@ -195,8 +192,9 @@ static int pcf50633_probe(struct i2c_client *client, ...@@ -195,8 +192,9 @@ static int pcf50633_probe(struct i2c_client *client,
const struct i2c_device_id *ids) const struct i2c_device_id *ids)
{ {
struct pcf50633 *pcf; struct pcf50633 *pcf;
struct platform_device *pdev;
struct pcf50633_platform_data *pdata = dev_get_platdata(&client->dev); struct pcf50633_platform_data *pdata = dev_get_platdata(&client->dev);
int i, ret; int i, j, ret;
int version, variant; int version, variant;
if (!client->irq) { if (!client->irq) {
...@@ -243,9 +241,6 @@ static int pcf50633_probe(struct i2c_client *client, ...@@ -243,9 +241,6 @@ static int pcf50633_probe(struct i2c_client *client,
for (i = 0; i < PCF50633_NUM_REGULATORS; i++) { for (i = 0; i < PCF50633_NUM_REGULATORS; i++) {
struct platform_device *pdev;
int j;
pdev = platform_device_alloc("pcf50633-regulator", i); pdev = platform_device_alloc("pcf50633-regulator", i);
if (!pdev) if (!pdev)
return -ENOMEM; return -ENOMEM;
...@@ -253,25 +248,31 @@ static int pcf50633_probe(struct i2c_client *client, ...@@ -253,25 +248,31 @@ static int pcf50633_probe(struct i2c_client *client,
pdev->dev.parent = pcf->dev; pdev->dev.parent = pcf->dev;
ret = platform_device_add_data(pdev, &pdata->reg_init_data[i], ret = platform_device_add_data(pdev, &pdata->reg_init_data[i],
sizeof(pdata->reg_init_data[i])); sizeof(pdata->reg_init_data[i]));
if (ret) { if (ret)
platform_device_put(pdev); goto err;
for (j = 0; j < i; j++)
platform_device_put(pcf->regulator_pdev[j]); ret = platform_device_add(pdev);
return ret; if (ret)
} goto err;
pcf->regulator_pdev[i] = pdev;
platform_device_add(pdev); pcf->regulator_pdev[i] = pdev;
} }
ret = sysfs_create_group(&client->dev.kobj, &pcf_attr_group); ret = sysfs_create_group(&client->dev.kobj, &pcf_attr_group);
if (ret) if (ret)
dev_err(pcf->dev, "error creating sysfs entries\n"); dev_warn(pcf->dev, "error creating sysfs entries\n");
if (pdata->probe_done) if (pdata->probe_done)
pdata->probe_done(pcf); pdata->probe_done(pcf);
return 0; return 0;
err:
platform_device_put(pdev);
for (j = 0; j < i; j++)
platform_device_put(pcf->regulator_pdev[j]);
return ret;
} }
static int pcf50633_remove(struct i2c_client *client) static int pcf50633_remove(struct i2c_client *client)
......
/*
* Copyright (c) 2014, The Linux Foundation. All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 and
* only version 2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/spmi.h>
#include <linux/regmap.h>
#include <linux/of_platform.h>
static const struct regmap_config spmi_regmap_config = {
.reg_bits = 16,
.val_bits = 8,
.max_register = 0xffff,
.fast_io = true,
};
static int pmic_spmi_probe(struct spmi_device *sdev)
{
struct device_node *root = sdev->dev.of_node;
struct regmap *regmap;
regmap = devm_regmap_init_spmi_ext(sdev, &spmi_regmap_config);
if (IS_ERR(regmap))
return PTR_ERR(regmap);
return of_platform_populate(root, NULL, NULL, &sdev->dev);
}
static void pmic_spmi_remove(struct spmi_device *sdev)
{
of_platform_depopulate(&sdev->dev);
}
static const struct of_device_id pmic_spmi_id_table[] = {
{ .compatible = "qcom,spmi-pmic" },
{ .compatible = "qcom,pm8941" },
{ .compatible = "qcom,pm8841" },
{ .compatible = "qcom,pma8084" },
{ }
};
MODULE_DEVICE_TABLE(of, pmic_spmi_id_table);
static struct spmi_driver pmic_spmi_driver = {
.probe = pmic_spmi_probe,
.remove = pmic_spmi_remove,
.driver = {
.name = "pmic-spmi",
.of_match_table = pmic_spmi_id_table,
},
};
module_spmi_driver(pmic_spmi_driver);
MODULE_DESCRIPTION("Qualcomm SPMI PMIC driver");
MODULE_ALIAS("spmi:spmi-pmic");
MODULE_LICENSE("GPL v2");
MODULE_AUTHOR("Josh Cartwright <joshc@codeaurora.org>");
MODULE_AUTHOR("Stanimir Varbanov <svarbanov@mm-sol.com>");
/*
* MFD core driver for Rockchip RK808
*
* Copyright (c) 2014, Fuzhou Rockchip Electronics Co., Ltd
*
* Author: Chris Zhong <zyw@rock-chips.com>
* Author: Zhang Qing <zhangqing@rock-chips.com>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
* version 2, as published by the Free Software Foundation.
*
* This program is distributed in the hope it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*/
#include <linux/i2c.h>
#include <linux/interrupt.h>
#include <linux/mfd/rk808.h>
#include <linux/mfd/core.h>
#include <linux/module.h>
#include <linux/regmap.h>
struct rk808_reg_data {
int addr;
int mask;
int value;
};
static bool rk808_is_volatile_reg(struct device *dev, unsigned int reg)
{
/*
* Notes:
* - Technically the ROUND_30s bit makes RTC_CTRL_REG volatile, but
* we don't use that feature. It's better to cache.
* - It's unlikely we care that RK808_DEVCTRL_REG is volatile since
* bits are cleared in case when we shutoff anyway, but better safe.
*/
switch (reg) {
case RK808_SECONDS_REG ... RK808_WEEKS_REG:
case RK808_RTC_STATUS_REG:
case RK808_VB_MON_REG:
case RK808_THERMAL_REG:
case RK808_DCDC_UV_STS_REG:
case RK808_LDO_UV_STS_REG:
case RK808_DCDC_PG_REG:
case RK808_LDO_PG_REG:
case RK808_DEVCTRL_REG:
case RK808_INT_STS_REG1:
case RK808_INT_STS_REG2:
return true;
}
return false;
}
static const struct regmap_config rk808_regmap_config = {
.reg_bits = 8,
.val_bits = 8,
.max_register = RK808_IO_POL_REG,
.cache_type = REGCACHE_RBTREE,
.volatile_reg = rk808_is_volatile_reg,
};
static struct resource rtc_resources[] = {
{
.start = RK808_IRQ_RTC_ALARM,
.end = RK808_IRQ_RTC_ALARM,
.flags = IORESOURCE_IRQ,
}
};
static const struct mfd_cell rk808s[] = {
{ .name = "rk808-clkout", },
{ .name = "rk808-regulator", },
{
.name = "rk808-rtc",
.num_resources = ARRAY_SIZE(rtc_resources),
.resources = &rtc_resources[0],
},
};
static const struct rk808_reg_data pre_init_reg[] = {
{ RK808_BUCK3_CONFIG_REG, BUCK_ILMIN_MASK, BUCK_ILMIN_150MA },
{ RK808_BUCK4_CONFIG_REG, BUCK_ILMIN_MASK, BUCK_ILMIN_200MA },
{ RK808_BOOST_CONFIG_REG, BOOST_ILMIN_MASK, BOOST_ILMIN_100MA },
{ RK808_BUCK1_CONFIG_REG, BUCK1_RATE_MASK, BUCK_ILMIN_200MA },
{ RK808_BUCK2_CONFIG_REG, BUCK2_RATE_MASK, BUCK_ILMIN_200MA },
{ RK808_VB_MON_REG, MASK_ALL, VB_LO_ACT |
VB_LO_SEL_3500MV },
};
static const struct regmap_irq rk808_irqs[] = {
/* INT_STS */
[RK808_IRQ_VOUT_LO] = {
.mask = RK808_IRQ_VOUT_LO_MSK,
.reg_offset = 0,
},
[RK808_IRQ_VB_LO] = {
.mask = RK808_IRQ_VB_LO_MSK,
.reg_offset = 0,
},
[RK808_IRQ_PWRON] = {
.mask = RK808_IRQ_PWRON_MSK,
.reg_offset = 0,
},
[RK808_IRQ_PWRON_LP] = {
.mask = RK808_IRQ_PWRON_LP_MSK,
.reg_offset = 0,
},
[RK808_IRQ_HOTDIE] = {
.mask = RK808_IRQ_HOTDIE_MSK,
.reg_offset = 0,
},
[RK808_IRQ_RTC_ALARM] = {
.mask = RK808_IRQ_RTC_ALARM_MSK,
.reg_offset = 0,
},
[RK808_IRQ_RTC_PERIOD] = {
.mask = RK808_IRQ_RTC_PERIOD_MSK,
.reg_offset = 0,
},
/* INT_STS2 */
[RK808_IRQ_PLUG_IN_INT] = {
.mask = RK808_IRQ_PLUG_IN_INT_MSK,
.reg_offset = 1,
},
[RK808_IRQ_PLUG_OUT_INT] = {
.mask = RK808_IRQ_PLUG_OUT_INT_MSK,
.reg_offset = 1,
},
};
static struct regmap_irq_chip rk808_irq_chip = {
.name = "rk808",
.irqs = rk808_irqs,
.num_irqs = ARRAY_SIZE(rk808_irqs),
.num_regs = 2,
.irq_reg_stride = 2,
.status_base = RK808_INT_STS_REG1,
.mask_base = RK808_INT_STS_MSK_REG1,
.ack_base = RK808_INT_STS_REG1,
.init_ack_masked = true,
};
static struct i2c_client *rk808_i2c_client;
static void rk808_device_shutdown(void)
{
int ret;
struct rk808 *rk808 = i2c_get_clientdata(rk808_i2c_client);
if (!rk808) {
dev_warn(&rk808_i2c_client->dev,
"have no rk808, so do nothing here\n");
return;
}
ret = regmap_update_bits(rk808->regmap,
RK808_DEVCTRL_REG,
DEV_OFF_RST, DEV_OFF_RST);
if (ret)
dev_err(&rk808_i2c_client->dev, "power off error!\n");
}
static int rk808_probe(struct i2c_client *client,
const struct i2c_device_id *id)
{
struct device_node *np = client->dev.of_node;
struct rk808 *rk808;
int pm_off = 0;
int ret;
int i;
if (!client->irq) {
dev_err(&client->dev, "No interrupt support, no core IRQ\n");
return -EINVAL;
}
rk808 = devm_kzalloc(&client->dev, sizeof(*rk808), GFP_KERNEL);
if (!rk808)
return -ENOMEM;
rk808->regmap = devm_regmap_init_i2c(client, &rk808_regmap_config);
if (IS_ERR(rk808->regmap)) {
dev_err(&client->dev, "regmap initialization failed\n");
return PTR_ERR(rk808->regmap);
}
for (i = 0; i < ARRAY_SIZE(pre_init_reg); i++) {
ret = regmap_update_bits(rk808->regmap, pre_init_reg[i].addr,
pre_init_reg[i].mask,
pre_init_reg[i].value);
if (ret) {
dev_err(&client->dev,
"0x%x write err\n", pre_init_reg[i].addr);
return ret;
}
}
ret = regmap_add_irq_chip(rk808->regmap, client->irq,
IRQF_ONESHOT, -1,
&rk808_irq_chip, &rk808->irq_data);
if (ret) {
dev_err(&client->dev, "Failed to add irq_chip %d\n", ret);
return ret;
}
rk808->i2c = client;
i2c_set_clientdata(client, rk808);
ret = mfd_add_devices(&client->dev, -1,
rk808s, ARRAY_SIZE(rk808s),
NULL, 0, regmap_irq_get_domain(rk808->irq_data));
if (ret) {
dev_err(&client->dev, "failed to add MFD devices %d\n", ret);
goto err_irq;
}
pm_off = of_property_read_bool(np,
"rockchip,system-power-controller");
if (pm_off && !pm_power_off) {
rk808_i2c_client = client;
pm_power_off = rk808_device_shutdown;
}
return 0;
err_irq:
regmap_del_irq_chip(client->irq, rk808->irq_data);
return ret;
}
static int rk808_remove(struct i2c_client *client)
{
struct rk808 *rk808 = i2c_get_clientdata(client);
regmap_del_irq_chip(client->irq, rk808->irq_data);
mfd_remove_devices(&client->dev);
pm_power_off = NULL;
return 0;
}
static struct of_device_id rk808_of_match[] = {
{ .compatible = "rockchip,rk808" },
{ },
};
MODULE_DEVICE_TABLE(of, rk808_of_match);
static const struct i2c_device_id rk808_ids[] = {
{ "rk808" },
{ },
};
MODULE_DEVICE_TABLE(i2c, rk808_ids);
static struct i2c_driver rk808_i2c_driver = {
.driver = {
.name = "rk808",
.of_match_table = rk808_of_match,
},
.probe = rk808_probe,
.remove = rk808_remove,
.id_table = rk808_ids,
};
module_i2c_driver(rk808_i2c_driver);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Chris Zhong <zyw@rock-chips.com>");
MODULE_AUTHOR("Zhang Qing <zhangqing@rock-chips.com>");
MODULE_DESCRIPTION("RK808 PMIC driver");
/*
* MFD core driver for Ricoh RN5T618 PMIC
*
* Copyright (C) 2014 Beniamino Galvani <b.galvani@gmail.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <linux/i2c.h>
#include <linux/mfd/core.h>
#include <linux/mfd/rn5t618.h>
#include <linux/module.h>
#include <linux/regmap.h>
static const struct mfd_cell rn5t618_cells[] = {
{ .name = "rn5t618-regulator" },
{ .name = "rn5t618-wdt" },
};
static bool rn5t618_volatile_reg(struct device *dev, unsigned int reg)
{
switch (reg) {
case RN5T618_WATCHDOGCNT:
case RN5T618_DCIRQ:
case RN5T618_ILIMDATAH ... RN5T618_AIN0DATAL:
case RN5T618_IR_ADC1 ... RN5T618_IR_ADC3:
case RN5T618_IR_GPR:
case RN5T618_IR_GPF:
case RN5T618_MON_IOIN:
case RN5T618_INTMON:
return true;
default:
return false;
}
}
static const struct regmap_config rn5t618_regmap_config = {
.reg_bits = 8,
.val_bits = 8,
.volatile_reg = rn5t618_volatile_reg,
.max_register = RN5T618_MAX_REG,
.cache_type = REGCACHE_RBTREE,
};
static struct rn5t618 *rn5t618_pm_power_off;
static void rn5t618_power_off(void)
{
/* disable automatic repower-on */
regmap_update_bits(rn5t618_pm_power_off->regmap, RN5T618_REPCNT,
RN5T618_REPCNT_REPWRON, 0);
/* start power-off sequence */
regmap_update_bits(rn5t618_pm_power_off->regmap, RN5T618_SLPCNT,
RN5T618_SLPCNT_SWPWROFF, RN5T618_SLPCNT_SWPWROFF);
}
static int rn5t618_i2c_probe(struct i2c_client *i2c,
const struct i2c_device_id *id)
{
struct rn5t618 *priv;
int ret;
priv = devm_kzalloc(&i2c->dev, sizeof(*priv), GFP_KERNEL);
if (!priv)
return -ENOMEM;
i2c_set_clientdata(i2c, priv);
priv->regmap = devm_regmap_init_i2c(i2c, &rn5t618_regmap_config);
if (IS_ERR(priv->regmap)) {
ret = PTR_ERR(priv->regmap);
dev_err(&i2c->dev, "regmap init failed: %d\n", ret);
return ret;
}
ret = mfd_add_devices(&i2c->dev, -1, rn5t618_cells,
ARRAY_SIZE(rn5t618_cells), NULL, 0, NULL);
if (ret) {
dev_err(&i2c->dev, "failed to add sub-devices: %d\n", ret);
return ret;
}
if (!pm_power_off) {
rn5t618_pm_power_off = priv;
pm_power_off = rn5t618_power_off;
}
return 0;
}
static int rn5t618_i2c_remove(struct i2c_client *i2c)
{
struct rn5t618 *priv = i2c_get_clientdata(i2c);
if (priv == rn5t618_pm_power_off) {
rn5t618_pm_power_off = NULL;
pm_power_off = NULL;
}
mfd_remove_devices(&i2c->dev);
return 0;
}
static const struct of_device_id rn5t618_of_match[] = {
{ .compatible = "ricoh,rn5t618" },
{ }
};
MODULE_DEVICE_TABLE(of, rn5t618_of_match);
static const struct i2c_device_id rn5t618_i2c_id[] = {
{ }
};
MODULE_DEVICE_TABLE(i2c, rn5t618_i2c_id);
static struct i2c_driver rn5t618_i2c_driver = {
.driver = {
.name = "rn5t618",
.of_match_table = of_match_ptr(rn5t618_of_match),
},
.probe = rn5t618_i2c_probe,
.remove = rn5t618_i2c_remove,
.id_table = rn5t618_i2c_id,
};
module_i2c_driver(rn5t618_i2c_driver);
MODULE_AUTHOR("Beniamino Galvani <b.galvani@gmail.com>");
MODULE_DESCRIPTION("Ricoh RN5T618 MFD driver");
MODULE_LICENSE("GPL v2");
...@@ -1197,7 +1197,7 @@ static int rtsx_pci_probe(struct pci_dev *pcidev, ...@@ -1197,7 +1197,7 @@ static int rtsx_pci_probe(struct pci_dev *pcidev,
pcr->msi_en = msi_en; pcr->msi_en = msi_en;
if (pcr->msi_en) { if (pcr->msi_en) {
ret = pci_enable_msi(pcidev); ret = pci_enable_msi(pcidev);
if (ret < 0) if (ret)
pcr->msi_en = false; pcr->msi_en = false;
} }
......
...@@ -684,7 +684,7 @@ static int rtsx_usb_suspend(struct usb_interface *intf, pm_message_t message) ...@@ -684,7 +684,7 @@ static int rtsx_usb_suspend(struct usb_interface *intf, pm_message_t message)
struct rtsx_ucr *ucr = struct rtsx_ucr *ucr =
(struct rtsx_ucr *)usb_get_intfdata(intf); (struct rtsx_ucr *)usb_get_intfdata(intf);
dev_dbg(&intf->dev, "%s called with pm message 0x%04u\n", dev_dbg(&intf->dev, "%s called with pm message 0x%04x\n",
__func__, message.event); __func__, message.event);
/* /*
......
...@@ -514,9 +514,9 @@ unsigned long sm501_set_clock(struct device *dev, ...@@ -514,9 +514,9 @@ unsigned long sm501_set_clock(struct device *dev,
unsigned long mode = smc501_readl(sm->regs + SM501_POWER_MODE_CONTROL); unsigned long mode = smc501_readl(sm->regs + SM501_POWER_MODE_CONTROL);
unsigned long gate = smc501_readl(sm->regs + SM501_CURRENT_GATE); unsigned long gate = smc501_readl(sm->regs + SM501_CURRENT_GATE);
unsigned long clock = smc501_readl(sm->regs + SM501_CURRENT_CLOCK); unsigned long clock = smc501_readl(sm->regs + SM501_CURRENT_CLOCK);
unsigned char reg;
unsigned int pll_reg = 0; unsigned int pll_reg = 0;
unsigned long sm501_freq; /* the actual frequency achieved */ unsigned long sm501_freq; /* the actual frequency achieved */
u64 reg;
struct sm501_clock to; struct sm501_clock to;
......
...@@ -249,7 +249,7 @@ int stmpe_set_altfunc(struct stmpe *stmpe, u32 pins, enum stmpe_block block) ...@@ -249,7 +249,7 @@ int stmpe_set_altfunc(struct stmpe *stmpe, u32 pins, enum stmpe_block block)
int af_bits = variant->af_bits; int af_bits = variant->af_bits;
int numregs = DIV_ROUND_UP(stmpe->num_gpios * af_bits, 8); int numregs = DIV_ROUND_UP(stmpe->num_gpios * af_bits, 8);
int mask = (1 << af_bits) - 1; int mask = (1 << af_bits) - 1;
u8 regs[numregs]; u8 regs[8];
int af, afperreg, ret; int af, afperreg, ret;
if (!variant->get_altfunc) if (!variant->get_altfunc)
...@@ -854,7 +854,7 @@ static irqreturn_t stmpe_irq(int irq, void *data) ...@@ -854,7 +854,7 @@ static irqreturn_t stmpe_irq(int irq, void *data)
struct stmpe_variant_info *variant = stmpe->variant; struct stmpe_variant_info *variant = stmpe->variant;
int num = DIV_ROUND_UP(variant->num_irqs, 8); int num = DIV_ROUND_UP(variant->num_irqs, 8);
u8 israddr; u8 israddr;
u8 isr[num]; u8 isr[3];
int ret; int ret;
int i; int i;
...@@ -1122,6 +1122,11 @@ static void stmpe_of_probe(struct stmpe_platform_data *pdata, ...@@ -1122,6 +1122,11 @@ static void stmpe_of_probe(struct stmpe_platform_data *pdata,
if (pdata->id < 0) if (pdata->id < 0)
pdata->id = -1; pdata->id = -1;
pdata->irq_gpio = of_get_named_gpio_flags(np, "irq-gpio", 0,
&pdata->irq_trigger);
if (gpio_is_valid(pdata->irq_gpio))
pdata->irq_over_gpio = 1;
else
pdata->irq_trigger = IRQF_TRIGGER_NONE; pdata->irq_trigger = IRQF_TRIGGER_NONE;
of_property_read_u32(np, "st,autosleep-timeout", of_property_read_u32(np, "st,autosleep-timeout",
......
...@@ -53,11 +53,11 @@ void am335x_tsc_se_set_cache(struct ti_tscadc_dev *tsadc, u32 val) ...@@ -53,11 +53,11 @@ void am335x_tsc_se_set_cache(struct ti_tscadc_dev *tsadc, u32 val)
unsigned long flags; unsigned long flags;
spin_lock_irqsave(&tsadc->reg_lock, flags); spin_lock_irqsave(&tsadc->reg_lock, flags);
tsadc->reg_se_cache = val; tsadc->reg_se_cache |= val;
if (tsadc->adc_waiting) if (tsadc->adc_waiting)
wake_up(&tsadc->reg_se_wait); wake_up(&tsadc->reg_se_wait);
else if (!tsadc->adc_in_use) else if (!tsadc->adc_in_use)
tscadc_writel(tsadc, REG_SE, val); tscadc_writel(tsadc, REG_SE, tsadc->reg_se_cache);
spin_unlock_irqrestore(&tsadc->reg_lock, flags); spin_unlock_irqrestore(&tsadc->reg_lock, flags);
} }
...@@ -96,6 +96,7 @@ static void am335x_tscadc_need_adc(struct ti_tscadc_dev *tsadc) ...@@ -96,6 +96,7 @@ static void am335x_tscadc_need_adc(struct ti_tscadc_dev *tsadc)
void am335x_tsc_se_set_once(struct ti_tscadc_dev *tsadc, u32 val) void am335x_tsc_se_set_once(struct ti_tscadc_dev *tsadc, u32 val)
{ {
spin_lock_irq(&tsadc->reg_lock); spin_lock_irq(&tsadc->reg_lock);
tsadc->reg_se_cache |= val;
am335x_tscadc_need_adc(tsadc); am335x_tscadc_need_adc(tsadc);
tscadc_writel(tsadc, REG_SE, val); tscadc_writel(tsadc, REG_SE, val);
...@@ -241,18 +242,20 @@ static int ti_tscadc_probe(struct platform_device *pdev) ...@@ -241,18 +242,20 @@ static int ti_tscadc_probe(struct platform_device *pdev)
tscadc_writel(tscadc, REG_CLKDIV, tscadc->clk_div); tscadc_writel(tscadc, REG_CLKDIV, tscadc->clk_div);
/* Set the control register bits */ /* Set the control register bits */
ctrl = CNTRLREG_STEPCONFIGWRT | ctrl = CNTRLREG_STEPCONFIGWRT | CNTRLREG_STEPID;
CNTRLREG_STEPID;
if (tsc_wires > 0)
ctrl |= CNTRLREG_4WIRE | CNTRLREG_TSCENB;
tscadc_writel(tscadc, REG_CTRL, ctrl); tscadc_writel(tscadc, REG_CTRL, ctrl);
/* Set register bits for Idle Config Mode */ /* Set register bits for Idle Config Mode */
if (tsc_wires > 0) if (tsc_wires > 0) {
tscadc->tsc_wires = tsc_wires;
if (tsc_wires == 5)
ctrl |= CNTRLREG_5WIRE | CNTRLREG_TSCENB;
else
ctrl |= CNTRLREG_4WIRE | CNTRLREG_TSCENB;
tscadc_idle_config(tscadc); tscadc_idle_config(tscadc);
}
/* Enable the TSC module enable bit */ /* Enable the TSC module enable bit */
ctrl = tscadc_readl(tscadc, REG_CTRL);
ctrl |= CNTRLREG_TSCSSENB; ctrl |= CNTRLREG_TSCSSENB;
tscadc_writel(tscadc, REG_CTRL, ctrl); tscadc_writel(tscadc, REG_CTRL, ctrl);
...@@ -324,21 +327,23 @@ static int tscadc_suspend(struct device *dev) ...@@ -324,21 +327,23 @@ static int tscadc_suspend(struct device *dev)
static int tscadc_resume(struct device *dev) static int tscadc_resume(struct device *dev)
{ {
struct ti_tscadc_dev *tscadc_dev = dev_get_drvdata(dev); struct ti_tscadc_dev *tscadc_dev = dev_get_drvdata(dev);
unsigned int restore, ctrl; u32 ctrl;
pm_runtime_get_sync(dev); pm_runtime_get_sync(dev);
/* context restore */ /* context restore */
ctrl = CNTRLREG_STEPCONFIGWRT | CNTRLREG_STEPID; ctrl = CNTRLREG_STEPCONFIGWRT | CNTRLREG_STEPID;
if (tscadc_dev->tsc_cell != -1)
ctrl |= CNTRLREG_TSCENB | CNTRLREG_4WIRE;
tscadc_writel(tscadc_dev, REG_CTRL, ctrl); tscadc_writel(tscadc_dev, REG_CTRL, ctrl);
if (tscadc_dev->tsc_cell != -1) if (tscadc_dev->tsc_cell != -1) {
if (tscadc_dev->tsc_wires == 5)
ctrl |= CNTRLREG_5WIRE | CNTRLREG_TSCENB;
else
ctrl |= CNTRLREG_4WIRE | CNTRLREG_TSCENB;
tscadc_idle_config(tscadc_dev); tscadc_idle_config(tscadc_dev);
restore = tscadc_readl(tscadc_dev, REG_CTRL); }
tscadc_writel(tscadc_dev, REG_CTRL, ctrl |= CNTRLREG_TSCSSENB;
(restore | CNTRLREG_TSCSSENB)); tscadc_writel(tscadc_dev, REG_CTRL, ctrl);
tscadc_writel(tscadc_dev, REG_CLKDIV, tscadc_dev->clk_div); tscadc_writel(tscadc_dev, REG_CLKDIV, tscadc_dev->clk_div);
......
...@@ -146,6 +146,8 @@ EXPORT_SYMBOL_GPL(tps65217_clear_bits); ...@@ -146,6 +146,8 @@ EXPORT_SYMBOL_GPL(tps65217_clear_bits);
static struct regmap_config tps65217_regmap_config = { static struct regmap_config tps65217_regmap_config = {
.reg_bits = 8, .reg_bits = 8,
.val_bits = 8, .val_bits = 8,
.max_register = TPS65217_REG_MAX,
}; };
static const struct of_device_id tps65217_of_match[] = { static const struct of_device_id tps65217_of_match[] = {
......
...@@ -486,6 +486,11 @@ static int tps65910_i2c_probe(struct i2c_client *i2c, ...@@ -486,6 +486,11 @@ static int tps65910_i2c_probe(struct i2c_client *i2c,
tps65910->i2c_client = i2c; tps65910->i2c_client = i2c;
tps65910->id = chip_id; tps65910->id = chip_id;
/* Work around silicon erratum SWCZ010: the tps65910 may miss the
* first I2C transfer. So issue a dummy transfer before the first
* real transfer.
*/
i2c_master_send(i2c, "", 1);
tps65910->regmap = devm_regmap_init_i2c(i2c, &tps65910_regmap_config); tps65910->regmap = devm_regmap_init_i2c(i2c, &tps65910_regmap_config);
if (IS_ERR(tps65910->regmap)) { if (IS_ERR(tps65910->regmap)) {
ret = PTR_ERR(tps65910->regmap); ret = PTR_ERR(tps65910->regmap);
......
...@@ -396,13 +396,17 @@ static int twl4030_init_sih_modules(unsigned line) ...@@ -396,13 +396,17 @@ static int twl4030_init_sih_modules(unsigned line)
status = twl_i2c_read(sih->module, rxbuf, status = twl_i2c_read(sih->module, rxbuf,
sih->mask[line].isr_offset, sih->bytes_ixr); sih->mask[line].isr_offset, sih->bytes_ixr);
if (status < 0) if (status < 0)
pr_err("twl4030: err %d initializing %s %s\n", pr_warn("twl4030: err %d initializing %s %s\n",
status, sih->name, "ISR"); status, sih->name, "ISR");
if (!sih->set_cor) if (!sih->set_cor) {
status = twl_i2c_write(sih->module, buf, status = twl_i2c_write(sih->module, buf,
sih->mask[line].isr_offset, sih->mask[line].isr_offset,
sih->bytes_ixr); sih->bytes_ixr);
if (status < 0)
pr_warn("twl4030: write failed: %d\n",
status);
}
/* /*
* else COR=1 means read sufficed. * else COR=1 means read sufficed.
* (for most SIH modules...) * (for most SIH modules...)
......
...@@ -627,6 +627,9 @@ static bool twl4030_power_use_poweroff(const struct twl4030_power_data *pdata, ...@@ -627,6 +627,9 @@ static bool twl4030_power_use_poweroff(const struct twl4030_power_data *pdata,
if (pdata && pdata->use_poweroff) if (pdata && pdata->use_poweroff)
return true; return true;
if (of_property_read_bool(node, "ti,system-power-controller"))
return true;
if (of_property_read_bool(node, "ti,use_poweroff")) if (of_property_read_bool(node, "ti,use_poweroff"))
return true; return true;
......
...@@ -679,6 +679,7 @@ static int twl6040_probe(struct i2c_client *client, ...@@ -679,6 +679,7 @@ static int twl6040_probe(struct i2c_client *client,
if (twl6040->rev < 0) { if (twl6040->rev < 0) {
dev_err(&client->dev, "Failed to read revision register: %d\n", dev_err(&client->dev, "Failed to read revision register: %d\n",
twl6040->rev); twl6040->rev);
ret = twl6040->rev;
goto gpio_err; goto gpio_err;
} }
......
...@@ -87,6 +87,7 @@ int wm5102_patch(struct arizona *arizona) ...@@ -87,6 +87,7 @@ int wm5102_patch(struct arizona *arizona)
case 0: case 0:
wm5102_patch = wm5102_reva_patch; wm5102_patch = wm5102_reva_patch;
patch_size = ARRAY_SIZE(wm5102_reva_patch); patch_size = ARRAY_SIZE(wm5102_reva_patch);
break;
default: default:
wm5102_patch = wm5102_revb_patch; wm5102_patch = wm5102_revb_patch;
patch_size = ARRAY_SIZE(wm5102_revb_patch); patch_size = ARRAY_SIZE(wm5102_revb_patch);
...@@ -245,9 +246,6 @@ const struct regmap_irq_chip wm5102_irq = { ...@@ -245,9 +246,6 @@ const struct regmap_irq_chip wm5102_irq = {
static const struct reg_default wm5102_reg_default[] = { static const struct reg_default wm5102_reg_default[] = {
{ 0x00000008, 0x0019 }, /* R8 - Ctrl IF SPI CFG 1 */ { 0x00000008, 0x0019 }, /* R8 - Ctrl IF SPI CFG 1 */
{ 0x00000009, 0x0001 }, /* R9 - Ctrl IF I2C1 CFG 1 */ { 0x00000009, 0x0001 }, /* R9 - Ctrl IF I2C1 CFG 1 */
{ 0x00000016, 0x0000 }, /* R22 - Write Sequencer Ctrl 0 */
{ 0x00000017, 0x0000 }, /* R23 - Write Sequencer Ctrl 1 */
{ 0x00000018, 0x0000 }, /* R24 - Write Sequencer Ctrl 2 */
{ 0x00000020, 0x0000 }, /* R32 - Tone Generator 1 */ { 0x00000020, 0x0000 }, /* R32 - Tone Generator 1 */
{ 0x00000021, 0x1000 }, /* R33 - Tone Generator 2 */ { 0x00000021, 0x1000 }, /* R33 - Tone Generator 2 */
{ 0x00000022, 0x0000 }, /* R34 - Tone Generator 3 */ { 0x00000022, 0x0000 }, /* R34 - Tone Generator 3 */
...@@ -1016,6 +1014,7 @@ static bool wm5102_readable_register(struct device *dev, unsigned int reg) ...@@ -1016,6 +1014,7 @@ static bool wm5102_readable_register(struct device *dev, unsigned int reg)
case ARIZONA_WRITE_SEQUENCER_CTRL_0: case ARIZONA_WRITE_SEQUENCER_CTRL_0:
case ARIZONA_WRITE_SEQUENCER_CTRL_1: case ARIZONA_WRITE_SEQUENCER_CTRL_1:
case ARIZONA_WRITE_SEQUENCER_CTRL_2: case ARIZONA_WRITE_SEQUENCER_CTRL_2:
case ARIZONA_WRITE_SEQUENCER_CTRL_3:
case ARIZONA_WRITE_SEQUENCER_PROM: case ARIZONA_WRITE_SEQUENCER_PROM:
case ARIZONA_TONE_GENERATOR_1: case ARIZONA_TONE_GENERATOR_1:
case ARIZONA_TONE_GENERATOR_2: case ARIZONA_TONE_GENERATOR_2:
...@@ -1060,6 +1059,8 @@ static bool wm5102_readable_register(struct device *dev, unsigned int reg) ...@@ -1060,6 +1059,8 @@ static bool wm5102_readable_register(struct device *dev, unsigned int reg)
case ARIZONA_ASYNC_CLOCK_1: case ARIZONA_ASYNC_CLOCK_1:
case ARIZONA_ASYNC_SAMPLE_RATE_1: case ARIZONA_ASYNC_SAMPLE_RATE_1:
case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS: case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS:
case ARIZONA_ASYNC_SAMPLE_RATE_2:
case ARIZONA_ASYNC_SAMPLE_RATE_2_STATUS:
case ARIZONA_OUTPUT_SYSTEM_CLOCK: case ARIZONA_OUTPUT_SYSTEM_CLOCK:
case ARIZONA_OUTPUT_ASYNC_CLOCK: case ARIZONA_OUTPUT_ASYNC_CLOCK:
case ARIZONA_RATE_ESTIMATOR_1: case ARIZONA_RATE_ESTIMATOR_1:
...@@ -1880,6 +1881,10 @@ static bool wm5102_volatile_register(struct device *dev, unsigned int reg) ...@@ -1880,6 +1881,10 @@ static bool wm5102_volatile_register(struct device *dev, unsigned int reg)
switch (reg) { switch (reg) {
case ARIZONA_SOFTWARE_RESET: case ARIZONA_SOFTWARE_RESET:
case ARIZONA_DEVICE_REVISION: case ARIZONA_DEVICE_REVISION:
case ARIZONA_WRITE_SEQUENCER_CTRL_0:
case ARIZONA_WRITE_SEQUENCER_CTRL_1:
case ARIZONA_WRITE_SEQUENCER_CTRL_2:
case ARIZONA_WRITE_SEQUENCER_CTRL_3:
case ARIZONA_OUTPUT_STATUS_1: case ARIZONA_OUTPUT_STATUS_1:
case ARIZONA_RAW_OUTPUT_STATUS_1: case ARIZONA_RAW_OUTPUT_STATUS_1:
case ARIZONA_SLIMBUS_RX_PORT_STATUS: case ARIZONA_SLIMBUS_RX_PORT_STATUS:
...@@ -1889,8 +1894,13 @@ static bool wm5102_volatile_register(struct device *dev, unsigned int reg) ...@@ -1889,8 +1894,13 @@ static bool wm5102_volatile_register(struct device *dev, unsigned int reg)
case ARIZONA_SAMPLE_RATE_3_STATUS: case ARIZONA_SAMPLE_RATE_3_STATUS:
case ARIZONA_HAPTICS_STATUS: case ARIZONA_HAPTICS_STATUS:
case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS: case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS:
case ARIZONA_ASYNC_SAMPLE_RATE_2_STATUS:
case ARIZONA_FLL1_NCO_TEST_0: case ARIZONA_FLL1_NCO_TEST_0:
case ARIZONA_FLL2_NCO_TEST_0: case ARIZONA_FLL2_NCO_TEST_0:
case ARIZONA_DAC_COMP_1:
case ARIZONA_DAC_COMP_2:
case ARIZONA_DAC_COMP_3:
case ARIZONA_DAC_COMP_4:
case ARIZONA_FX_CTRL2: case ARIZONA_FX_CTRL2:
case ARIZONA_INTERRUPT_STATUS_1: case ARIZONA_INTERRUPT_STATUS_1:
case ARIZONA_INTERRUPT_STATUS_2: case ARIZONA_INTERRUPT_STATUS_2:
......
...@@ -666,9 +666,6 @@ static const struct reg_default wm5110_reg_default[] = { ...@@ -666,9 +666,6 @@ static const struct reg_default wm5110_reg_default[] = {
{ 0x0000000A, 0x0001 }, /* R10 - Ctrl IF I2C2 CFG 1 */ { 0x0000000A, 0x0001 }, /* R10 - Ctrl IF I2C2 CFG 1 */
{ 0x0000000B, 0x0036 }, /* R11 - Ctrl IF I2C1 CFG 2 */ { 0x0000000B, 0x0036 }, /* R11 - Ctrl IF I2C1 CFG 2 */
{ 0x0000000C, 0x0036 }, /* R12 - Ctrl IF I2C2 CFG 2 */ { 0x0000000C, 0x0036 }, /* R12 - Ctrl IF I2C2 CFG 2 */
{ 0x00000016, 0x0000 }, /* R22 - Write Sequencer Ctrl 0 */
{ 0x00000017, 0x0000 }, /* R23 - Write Sequencer Ctrl 1 */
{ 0x00000018, 0x0000 }, /* R24 - Write Sequencer Ctrl 2 */
{ 0x00000020, 0x0000 }, /* R32 - Tone Generator 1 */ { 0x00000020, 0x0000 }, /* R32 - Tone Generator 1 */
{ 0x00000021, 0x1000 }, /* R33 - Tone Generator 2 */ { 0x00000021, 0x1000 }, /* R33 - Tone Generator 2 */
{ 0x00000022, 0x0000 }, /* R34 - Tone Generator 3 */ { 0x00000022, 0x0000 }, /* R34 - Tone Generator 3 */
...@@ -705,6 +702,7 @@ static const struct reg_default wm5110_reg_default[] = { ...@@ -705,6 +702,7 @@ static const struct reg_default wm5110_reg_default[] = {
{ 0x00000104, 0x0011 }, /* R260 - Sample rate 3 */ { 0x00000104, 0x0011 }, /* R260 - Sample rate 3 */
{ 0x00000112, 0x0305 }, /* R274 - Async clock 1 */ { 0x00000112, 0x0305 }, /* R274 - Async clock 1 */
{ 0x00000113, 0x0011 }, /* R275 - Async sample rate 1 */ { 0x00000113, 0x0011 }, /* R275 - Async sample rate 1 */
{ 0x00000114, 0x0011 }, /* R276 - Async sample rate 2 */
{ 0x00000149, 0x0000 }, /* R329 - Output system clock */ { 0x00000149, 0x0000 }, /* R329 - Output system clock */
{ 0x0000014A, 0x0000 }, /* R330 - Output async clock */ { 0x0000014A, 0x0000 }, /* R330 - Output async clock */
{ 0x00000152, 0x0000 }, /* R338 - Rate Estimator 1 */ { 0x00000152, 0x0000 }, /* R338 - Rate Estimator 1 */
...@@ -1741,6 +1739,8 @@ static bool wm5110_readable_register(struct device *dev, unsigned int reg) ...@@ -1741,6 +1739,8 @@ static bool wm5110_readable_register(struct device *dev, unsigned int reg)
case ARIZONA_ASYNC_CLOCK_1: case ARIZONA_ASYNC_CLOCK_1:
case ARIZONA_ASYNC_SAMPLE_RATE_1: case ARIZONA_ASYNC_SAMPLE_RATE_1:
case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS: case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS:
case ARIZONA_ASYNC_SAMPLE_RATE_2:
case ARIZONA_ASYNC_SAMPLE_RATE_2_STATUS:
case ARIZONA_OUTPUT_SYSTEM_CLOCK: case ARIZONA_OUTPUT_SYSTEM_CLOCK:
case ARIZONA_OUTPUT_ASYNC_CLOCK: case ARIZONA_OUTPUT_ASYNC_CLOCK:
case ARIZONA_RATE_ESTIMATOR_1: case ARIZONA_RATE_ESTIMATOR_1:
...@@ -2815,11 +2815,15 @@ static bool wm5110_volatile_register(struct device *dev, unsigned int reg) ...@@ -2815,11 +2815,15 @@ static bool wm5110_volatile_register(struct device *dev, unsigned int reg)
switch (reg) { switch (reg) {
case ARIZONA_SOFTWARE_RESET: case ARIZONA_SOFTWARE_RESET:
case ARIZONA_DEVICE_REVISION: case ARIZONA_DEVICE_REVISION:
case ARIZONA_WRITE_SEQUENCER_CTRL_0:
case ARIZONA_WRITE_SEQUENCER_CTRL_1:
case ARIZONA_WRITE_SEQUENCER_CTRL_2:
case ARIZONA_HAPTICS_STATUS: case ARIZONA_HAPTICS_STATUS:
case ARIZONA_SAMPLE_RATE_1_STATUS: case ARIZONA_SAMPLE_RATE_1_STATUS:
case ARIZONA_SAMPLE_RATE_2_STATUS: case ARIZONA_SAMPLE_RATE_2_STATUS:
case ARIZONA_SAMPLE_RATE_3_STATUS: case ARIZONA_SAMPLE_RATE_3_STATUS:
case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS: case ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS:
case ARIZONA_ASYNC_SAMPLE_RATE_2_STATUS:
case ARIZONA_MIC_DETECT_3: case ARIZONA_MIC_DETECT_3:
case ARIZONA_HEADPHONE_DETECT_2: case ARIZONA_HEADPHONE_DETECT_2:
case ARIZONA_INPUT_ENABLES_STATUS: case ARIZONA_INPUT_ENABLES_STATUS:
......
...@@ -262,8 +262,10 @@ int wm8994_irq_init(struct wm8994 *wm8994) ...@@ -262,8 +262,10 @@ int wm8994_irq_init(struct wm8994 *wm8994)
return 0; return 0;
} }
EXPORT_SYMBOL(wm8994_irq_init);
void wm8994_irq_exit(struct wm8994 *wm8994) void wm8994_irq_exit(struct wm8994 *wm8994)
{ {
regmap_del_irq_chip(wm8994->irq, wm8994->irq_data); regmap_del_irq_chip(wm8994->irq, wm8994->irq_data);
} }
EXPORT_SYMBOL(wm8994_irq_exit);
...@@ -1252,6 +1252,7 @@ struct regmap_config wm1811_regmap_config = { ...@@ -1252,6 +1252,7 @@ struct regmap_config wm1811_regmap_config = {
.volatile_reg = wm1811_volatile_register, .volatile_reg = wm1811_volatile_register,
.readable_reg = wm1811_readable_register, .readable_reg = wm1811_readable_register,
}; };
EXPORT_SYMBOL(wm1811_regmap_config);
struct regmap_config wm8994_regmap_config = { struct regmap_config wm8994_regmap_config = {
.reg_bits = 16, .reg_bits = 16,
...@@ -1266,6 +1267,7 @@ struct regmap_config wm8994_regmap_config = { ...@@ -1266,6 +1267,7 @@ struct regmap_config wm8994_regmap_config = {
.volatile_reg = wm8994_volatile_register, .volatile_reg = wm8994_volatile_register,
.readable_reg = wm8994_readable_register, .readable_reg = wm8994_readable_register,
}; };
EXPORT_SYMBOL(wm8994_regmap_config);
struct regmap_config wm8958_regmap_config = { struct regmap_config wm8958_regmap_config = {
.reg_bits = 16, .reg_bits = 16,
...@@ -1280,8 +1282,10 @@ struct regmap_config wm8958_regmap_config = { ...@@ -1280,8 +1282,10 @@ struct regmap_config wm8958_regmap_config = {
.volatile_reg = wm8958_volatile_register, .volatile_reg = wm8958_volatile_register,
.readable_reg = wm8958_readable_register, .readable_reg = wm8958_readable_register,
}; };
EXPORT_SYMBOL(wm8958_regmap_config);
struct regmap_config wm8994_base_regmap_config = { struct regmap_config wm8994_base_regmap_config = {
.reg_bits = 16, .reg_bits = 16,
.val_bits = 16, .val_bits = 16,
}; };
EXPORT_SYMBOL(wm8994_base_regmap_config);
/*
* This header provides constants clk index RK808 pmic clkout
*/
#ifndef _CLK_ROCKCHIP_RK808
#define _CLK_ROCKCHIP_RK808
/* CLOCKOUT index */
#define RK808_CLKOUT0 0
#define RK808_CLKOUT1 1
#endif
...@@ -27,6 +27,7 @@ ...@@ -27,6 +27,7 @@
#define ARIZONA_WRITE_SEQUENCER_CTRL_0 0x16 #define ARIZONA_WRITE_SEQUENCER_CTRL_0 0x16
#define ARIZONA_WRITE_SEQUENCER_CTRL_1 0x17 #define ARIZONA_WRITE_SEQUENCER_CTRL_1 0x17
#define ARIZONA_WRITE_SEQUENCER_CTRL_2 0x18 #define ARIZONA_WRITE_SEQUENCER_CTRL_2 0x18
#define ARIZONA_WRITE_SEQUENCER_CTRL_3 0x19
#define ARIZONA_WRITE_SEQUENCER_PROM 0x1A #define ARIZONA_WRITE_SEQUENCER_PROM 0x1A
#define ARIZONA_TONE_GENERATOR_1 0x20 #define ARIZONA_TONE_GENERATOR_1 0x20
#define ARIZONA_TONE_GENERATOR_2 0x21 #define ARIZONA_TONE_GENERATOR_2 0x21
...@@ -70,7 +71,9 @@ ...@@ -70,7 +71,9 @@
#define ARIZONA_SAMPLE_RATE_3_STATUS 0x10C #define ARIZONA_SAMPLE_RATE_3_STATUS 0x10C
#define ARIZONA_ASYNC_CLOCK_1 0x112 #define ARIZONA_ASYNC_CLOCK_1 0x112
#define ARIZONA_ASYNC_SAMPLE_RATE_1 0x113 #define ARIZONA_ASYNC_SAMPLE_RATE_1 0x113
#define ARIZONA_ASYNC_SAMPLE_RATE_2 0x114
#define ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS 0x11B #define ARIZONA_ASYNC_SAMPLE_RATE_1_STATUS 0x11B
#define ARIZONA_ASYNC_SAMPLE_RATE_2_STATUS 0x11C
#define ARIZONA_OUTPUT_SYSTEM_CLOCK 0x149 #define ARIZONA_OUTPUT_SYSTEM_CLOCK 0x149
#define ARIZONA_OUTPUT_ASYNC_CLOCK 0x14A #define ARIZONA_OUTPUT_ASYNC_CLOCK 0x14A
#define ARIZONA_RATE_ESTIMATOR_1 0x152 #define ARIZONA_RATE_ESTIMATOR_1 0x152
...@@ -1664,16 +1667,30 @@ ...@@ -1664,16 +1667,30 @@
/* /*
* R275 (0x113) - Async sample rate 1 * R275 (0x113) - Async sample rate 1
*/ */
#define ARIZONA_ASYNC_SAMPLE_RATE_MASK 0x001F /* ASYNC_SAMPLE_RATE - [4:0] */ #define ARIZONA_ASYNC_SAMPLE_RATE_1_MASK 0x001F /* ASYNC_SAMPLE_RATE_1 - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_SHIFT 0 /* ASYNC_SAMPLE_RATE - [4:0] */ #define ARIZONA_ASYNC_SAMPLE_RATE_1_SHIFT 0 /* ASYNC_SAMPLE_RATE_1 - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_WIDTH 5 /* ASYNC_SAMPLE_RATE - [4:0] */ #define ARIZONA_ASYNC_SAMPLE_RATE_1_WIDTH 5 /* ASYNC_SAMPLE_RATE_1 - [4:0] */
/*
* R276 (0x114) - Async sample rate 2
*/
#define ARIZONA_ASYNC_SAMPLE_RATE_2_MASK 0x001F /* ASYNC_SAMPLE_RATE_2 - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_2_SHIFT 0 /* ASYNC_SAMPLE_RATE_2 - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_2_WIDTH 5 /* ASYNC_SAMPLE_RATE_2 - [4:0] */
/* /*
* R283 (0x11B) - Async sample rate 1 status * R283 (0x11B) - Async sample rate 1 status
*/ */
#define ARIZONA_ASYNC_SAMPLE_RATE_STS_MASK 0x001F /* ASYNC_SAMPLE_RATE_STS - [4:0] */ #define ARIZONA_ASYNC_SAMPLE_RATE_1_STS_MASK 0x001F /* ASYNC_SAMPLE_RATE_1_STS - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_STS_SHIFT 0 /* ASYNC_SAMPLE_RATE_STS - [4:0] */ #define ARIZONA_ASYNC_SAMPLE_RATE_1_STS_SHIFT 0 /* ASYNC_SAMPLE_RATE_1_STS - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_STS_WIDTH 5 /* ASYNC_SAMPLE_RATE_STS - [4:0] */ #define ARIZONA_ASYNC_SAMPLE_RATE_1_STS_WIDTH 5 /* ASYNC_SAMPLE_RATE_1_STS - [4:0] */
/*
* R284 (0x11C) - Async sample rate 2 status
*/
#define ARIZONA_ASYNC_SAMPLE_RATE_2_STS_MASK 0x001F /* ASYNC_SAMPLE_RATE_2_STS - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_2_STS_SHIFT 0 /* ASYNC_SAMPLE_RATE_2_STS - [4:0] */
#define ARIZONA_ASYNC_SAMPLE_RATE_2_STS_WIDTH 5 /* ASYNC_SAMPLE_RATE_2_STS - [4:0] */
/* /*
* R329 (0x149) - Output system clock * R329 (0x149) - Output system clock
......
...@@ -44,6 +44,9 @@ struct mfd_cell { ...@@ -44,6 +44,9 @@ struct mfd_cell {
*/ */
const char *of_compatible; const char *of_compatible;
/* Matches ACPI PNP id, either _HID or _CID */
const char *acpi_pnpid;
/* /*
* These resources can be specified relative to the parent device. * These resources can be specified relative to the parent device.
* For accessing hardware you should use resources from the platform dev * For accessing hardware you should use resources from the platform dev
......
...@@ -62,10 +62,6 @@ struct cros_ec_command { ...@@ -62,10 +62,6 @@ struct cros_ec_command {
* @dev: Device pointer * @dev: Device pointer
* @was_wake_device: true if this device was set to wake the system from * @was_wake_device: true if this device was set to wake the system from
* sleep at the last suspend * sleep at the last suspend
* @cmd_xfer: send command to EC and get response
* Returns the number of bytes received if the communication succeeded, but
* that doesn't mean the EC was happy with the command. The caller
* should check msg.result for the EC's result code.
* *
* @priv: Private data * @priv: Private data
* @irq: Interrupt to use * @irq: Interrupt to use
...@@ -82,6 +78,10 @@ struct cros_ec_command { ...@@ -82,6 +78,10 @@ struct cros_ec_command {
* @dout_size: size of dout buffer to allocate (zero to use static dout) * @dout_size: size of dout buffer to allocate (zero to use static dout)
* @parent: pointer to parent device (e.g. i2c or spi device) * @parent: pointer to parent device (e.g. i2c or spi device)
* @wake_enabled: true if this device can wake the system from sleep * @wake_enabled: true if this device can wake the system from sleep
* @cmd_xfer: send command to EC and get response
* Returns the number of bytes received if the communication succeeded, but
* that doesn't mean the EC was happy with the command. The caller
* should check msg.result for the EC's result code.
* @lock: one transaction at a time * @lock: one transaction at a time
*/ */
struct cros_ec_device { struct cros_ec_device {
...@@ -92,8 +92,6 @@ struct cros_ec_device { ...@@ -92,8 +92,6 @@ struct cros_ec_device {
struct device *dev; struct device *dev;
bool was_wake_device; bool was_wake_device;
struct class *cros_class; struct class *cros_class;
int (*cmd_xfer)(struct cros_ec_device *ec,
struct cros_ec_command *msg);
/* These are used to implement the platform-specific interface */ /* These are used to implement the platform-specific interface */
void *priv; void *priv;
...@@ -104,6 +102,8 @@ struct cros_ec_device { ...@@ -104,6 +102,8 @@ struct cros_ec_device {
int dout_size; int dout_size;
struct device *parent; struct device *parent;
bool wake_enabled; bool wake_enabled;
int (*cmd_xfer)(struct cros_ec_device *ec,
struct cros_ec_command *msg);
struct mutex lock; struct mutex lock;
}; };
...@@ -152,6 +152,18 @@ int cros_ec_prepare_tx(struct cros_ec_device *ec_dev, ...@@ -152,6 +152,18 @@ int cros_ec_prepare_tx(struct cros_ec_device *ec_dev,
int cros_ec_check_result(struct cros_ec_device *ec_dev, int cros_ec_check_result(struct cros_ec_device *ec_dev,
struct cros_ec_command *msg); struct cros_ec_command *msg);
/**
* cros_ec_cmd_xfer - Send a command to the ChromeOS EC
*
* Call this to send a command to the ChromeOS EC. This should be used
* instead of calling the EC's cmd_xfer() callback directly.
*
* @ec_dev: EC device
* @msg: Message to write
*/
int cros_ec_cmd_xfer(struct cros_ec_device *ec_dev,
struct cros_ec_command *msg);
/** /**
* cros_ec_remove - Remove a ChromeOS EC * cros_ec_remove - Remove a ChromeOS EC
* *
......
...@@ -211,7 +211,7 @@ static inline int da9052_reg_update(struct da9052 *da9052, unsigned char reg, ...@@ -211,7 +211,7 @@ static inline int da9052_reg_update(struct da9052 *da9052, unsigned char reg,
int da9052_device_init(struct da9052 *da9052, u8 chip_id); int da9052_device_init(struct da9052 *da9052, u8 chip_id);
void da9052_device_exit(struct da9052 *da9052); void da9052_device_exit(struct da9052 *da9052);
extern struct regmap_config da9052_regmap_config; extern const struct regmap_config da9052_regmap_config;
int da9052_irq_init(struct da9052 *da9052); int da9052_irq_init(struct da9052 *da9052);
int da9052_irq_exit(struct da9052 *da9052); int da9052_irq_exit(struct da9052 *da9052);
......
...@@ -21,7 +21,7 @@ ...@@ -21,7 +21,7 @@
*/ */
#ifndef __LINUX_MFD_DAVINCI_VOICECODEC_H_ #ifndef __LINUX_MFD_DAVINCI_VOICECODEC_H_
#define __LINUX_MFD_DAVINIC_VOICECODEC_H_ #define __LINUX_MFD_DAVINCI_VOICECODEC_H_
#include <linux/kernel.h> #include <linux/kernel.h>
#include <linux/platform_device.h> #include <linux/platform_device.h>
......
/*
* Header file for device driver Hi6421 PMIC
*
* Copyright (c) <2011-2014> HiSilicon Technologies Co., Ltd.
* http://www.hisilicon.com
* Copyright (c) <2013-2014> Linaro Ltd.
* http://www.linaro.org
*
* Author: Guodong Xu <guodong.xu@linaro.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __HI6421_PMIC_H
#define __HI6421_PMIC_H
/* Hi6421 registers are mapped to memory bus in 4 bytes stride */
#define HI6421_REG_TO_BUS_ADDR(x) (x << 2)
/* Hi6421 maximum register number */
#define HI6421_REG_MAX 0xFF
/* Hi6421 OCP (over current protection) and DEB (debounce) control register */
#define HI6421_OCP_DEB_CTRL_REG HI6421_REG_TO_BUS_ADDR(0x51)
#define HI6421_OCP_DEB_SEL_MASK 0x0C
#define HI6421_OCP_DEB_SEL_8MS 0x00
#define HI6421_OCP_DEB_SEL_16MS 0x04
#define HI6421_OCP_DEB_SEL_32MS 0x08
#define HI6421_OCP_DEB_SEL_64MS 0x0C
#define HI6421_OCP_EN_DEBOUNCE_MASK 0x02
#define HI6421_OCP_EN_DEBOUNCE_ENABLE 0x02
#define HI6421_OCP_AUTO_STOP_MASK 0x01
#define HI6421_OCP_AUTO_STOP_ENABLE 0x01
struct hi6421_pmic {
struct regmap *regmap;
};
#endif /* __HI6421_PMIC_H */
...@@ -46,7 +46,7 @@ enum max77693_pmic_reg { ...@@ -46,7 +46,7 @@ enum max77693_pmic_reg {
MAX77693_LED_REG_VOUT_FLASH2 = 0x0C, MAX77693_LED_REG_VOUT_FLASH2 = 0x0C,
MAX77693_LED_REG_FLASH_INT = 0x0E, MAX77693_LED_REG_FLASH_INT = 0x0E,
MAX77693_LED_REG_FLASH_INT_MASK = 0x0F, MAX77693_LED_REG_FLASH_INT_MASK = 0x0F,
MAX77693_LED_REG_FLASH_INT_STATUS = 0x10, MAX77693_LED_REG_FLASH_STATUS = 0x10,
MAX77693_PMIC_REG_PMIC_ID1 = 0x20, MAX77693_PMIC_REG_PMIC_ID1 = 0x20,
MAX77693_PMIC_REG_PMIC_ID2 = 0x21, MAX77693_PMIC_REG_PMIC_ID2 = 0x21,
...@@ -85,6 +85,65 @@ enum max77693_pmic_reg { ...@@ -85,6 +85,65 @@ enum max77693_pmic_reg {
MAX77693_PMIC_REG_END, MAX77693_PMIC_REG_END,
}; };
/* MAX77693 ITORCH register */
#define TORCH_IOUT1_SHIFT 0
#define TORCH_IOUT2_SHIFT 4
#define TORCH_IOUT_MIN 15625
#define TORCH_IOUT_MAX 250000
#define TORCH_IOUT_STEP 15625
/* MAX77693 IFLASH1 and IFLASH2 registers */
#define FLASH_IOUT_MIN 15625
#define FLASH_IOUT_MAX_1LED 1000000
#define FLASH_IOUT_MAX_2LEDS 625000
#define FLASH_IOUT_STEP 15625
/* MAX77693 TORCH_TIMER register */
#define TORCH_TMR_NO_TIMER 0x40
#define TORCH_TIMEOUT_MIN 262000
#define TORCH_TIMEOUT_MAX 15728000
/* MAX77693 FLASH_TIMER register */
#define FLASH_TMR_LEVEL 0x80
#define FLASH_TIMEOUT_MIN 62500
#define FLASH_TIMEOUT_MAX 1000000
#define FLASH_TIMEOUT_STEP 62500
/* MAX77693 FLASH_EN register */
#define FLASH_EN_OFF 0x0
#define FLASH_EN_FLASH 0x1
#define FLASH_EN_TORCH 0x2
#define FLASH_EN_ON 0x3
#define FLASH_EN_SHIFT(x) (6 - ((x) - 1) * 2)
#define TORCH_EN_SHIFT(x) (2 - ((x) - 1) * 2)
/* MAX77693 MAX_FLASH1 register */
#define MAX_FLASH1_MAX_FL_EN 0x80
#define MAX_FLASH1_VSYS_MIN 2400
#define MAX_FLASH1_VSYS_MAX 3400
#define MAX_FLASH1_VSYS_STEP 33
/* MAX77693 VOUT_CNTL register */
#define FLASH_BOOST_FIXED 0x04
#define FLASH_BOOST_LEDNUM_2 0x80
/* MAX77693 VOUT_FLASH1 register */
#define FLASH_VOUT_MIN 3300
#define FLASH_VOUT_MAX 5500
#define FLASH_VOUT_STEP 25
#define FLASH_VOUT_RMIN 0x0c
/* MAX77693 FLASH_STATUS register */
#define FLASH_STATUS_FLASH_ON BIT(3)
#define FLASH_STATUS_TORCH_ON BIT(2)
/* MAX77693 FLASH_INT register */
#define FLASH_INT_FLED2_OPEN BIT(0)
#define FLASH_INT_FLED2_SHORT BIT(1)
#define FLASH_INT_FLED1_OPEN BIT(2)
#define FLASH_INT_FLED1_SHORT BIT(3)
#define FLASH_INT_OVER_CURRENT BIT(4)
/* MAX77693 CHG_CNFG_00 register */ /* MAX77693 CHG_CNFG_00 register */
#define CHG_CNFG_00_CHG_MASK 0x1 #define CHG_CNFG_00_CHG_MASK 0x1
#define CHG_CNFG_00_BUCK_MASK 0x4 #define CHG_CNFG_00_BUCK_MASK 0x4
......
...@@ -63,6 +63,45 @@ struct max77693_muic_platform_data { ...@@ -63,6 +63,45 @@ struct max77693_muic_platform_data {
int path_uart; int path_uart;
}; };
/* MAX77693 led flash */
/* triggers */
enum max77693_led_trigger {
MAX77693_LED_TRIG_OFF,
MAX77693_LED_TRIG_FLASH,
MAX77693_LED_TRIG_TORCH,
MAX77693_LED_TRIG_EXT,
MAX77693_LED_TRIG_SOFT,
};
/* trigger types */
enum max77693_led_trigger_type {
MAX77693_LED_TRIG_TYPE_EDGE,
MAX77693_LED_TRIG_TYPE_LEVEL,
};
/* boost modes */
enum max77693_led_boost_mode {
MAX77693_LED_BOOST_NONE,
MAX77693_LED_BOOST_ADAPTIVE,
MAX77693_LED_BOOST_FIXED,
};
struct max77693_led_platform_data {
u32 fleds[2];
u32 iout_torch[2];
u32 iout_flash[2];
u32 trigger[2];
u32 trigger_type[2];
u32 num_leds;
u32 boost_mode;
u32 flash_timeout;
u32 boost_vout;
u32 low_vsys;
};
/* MAX77693 */
struct max77693_platform_data { struct max77693_platform_data {
/* regulator data */ /* regulator data */
struct max77693_regulator_data *regulators; struct max77693_regulator_data *regulators;
...@@ -70,5 +109,6 @@ struct max77693_platform_data { ...@@ -70,5 +109,6 @@ struct max77693_platform_data {
/* muic data */ /* muic data */
struct max77693_muic_platform_data *muic_data; struct max77693_muic_platform_data *muic_data;
struct max77693_led_platform_data *led_data;
}; };
#endif /* __LINUX_MFD_MAX77693_H */ #endif /* __LINUX_MFD_MAX77693_H */
/*
* rk808.h for Rockchip RK808
*
* Copyright (c) 2014, Fuzhou Rockchip Electronics Co., Ltd
*
* Author: Chris Zhong <zyw@rock-chips.com>
* Author: Zhang Qing <zhangqing@rock-chips.com>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
* version 2, as published by the Free Software Foundation.
*
* This program is distributed in the hope it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*/
#ifndef __LINUX_REGULATOR_rk808_H
#define __LINUX_REGULATOR_rk808_H
#include <linux/regulator/machine.h>
#include <linux/regmap.h>
/*
* rk808 Global Register Map.
*/
#define RK808_DCDC1 0 /* (0+RK808_START) */
#define RK808_LDO1 4 /* (4+RK808_START) */
#define RK808_NUM_REGULATORS 14
enum rk808_reg {
RK808_ID_DCDC1,
RK808_ID_DCDC2,
RK808_ID_DCDC3,
RK808_ID_DCDC4,
RK808_ID_LDO1,
RK808_ID_LDO2,
RK808_ID_LDO3,
RK808_ID_LDO4,
RK808_ID_LDO5,
RK808_ID_LDO6,
RK808_ID_LDO7,
RK808_ID_LDO8,
RK808_ID_SWITCH1,
RK808_ID_SWITCH2,
};
#define RK808_SECONDS_REG 0x00
#define RK808_MINUTES_REG 0x01
#define RK808_HOURS_REG 0x02
#define RK808_DAYS_REG 0x03
#define RK808_MONTHS_REG 0x04
#define RK808_YEARS_REG 0x05
#define RK808_WEEKS_REG 0x06
#define RK808_ALARM_SECONDS_REG 0x08
#define RK808_ALARM_MINUTES_REG 0x09
#define RK808_ALARM_HOURS_REG 0x0a
#define RK808_ALARM_DAYS_REG 0x0b
#define RK808_ALARM_MONTHS_REG 0x0c
#define RK808_ALARM_YEARS_REG 0x0d
#define RK808_RTC_CTRL_REG 0x10
#define RK808_RTC_STATUS_REG 0x11
#define RK808_RTC_INT_REG 0x12
#define RK808_RTC_COMP_LSB_REG 0x13
#define RK808_RTC_COMP_MSB_REG 0x14
#define RK808_CLK32OUT_REG 0x20
#define RK808_VB_MON_REG 0x21
#define RK808_THERMAL_REG 0x22
#define RK808_DCDC_EN_REG 0x23
#define RK808_LDO_EN_REG 0x24
#define RK808_SLEEP_SET_OFF_REG1 0x25
#define RK808_SLEEP_SET_OFF_REG2 0x26
#define RK808_DCDC_UV_STS_REG 0x27
#define RK808_DCDC_UV_ACT_REG 0x28
#define RK808_LDO_UV_STS_REG 0x29
#define RK808_LDO_UV_ACT_REG 0x2a
#define RK808_DCDC_PG_REG 0x2b
#define RK808_LDO_PG_REG 0x2c
#define RK808_VOUT_MON_TDB_REG 0x2d
#define RK808_BUCK1_CONFIG_REG 0x2e
#define RK808_BUCK1_ON_VSEL_REG 0x2f
#define RK808_BUCK1_SLP_VSEL_REG 0x30
#define RK808_BUCK1_DVS_VSEL_REG 0x31
#define RK808_BUCK2_CONFIG_REG 0x32
#define RK808_BUCK2_ON_VSEL_REG 0x33
#define RK808_BUCK2_SLP_VSEL_REG 0x34
#define RK808_BUCK2_DVS_VSEL_REG 0x35
#define RK808_BUCK3_CONFIG_REG 0x36
#define RK808_BUCK4_CONFIG_REG 0x37
#define RK808_BUCK4_ON_VSEL_REG 0x38
#define RK808_BUCK4_SLP_VSEL_REG 0x39
#define RK808_BOOST_CONFIG_REG 0x3a
#define RK808_LDO1_ON_VSEL_REG 0x3b
#define RK808_LDO1_SLP_VSEL_REG 0x3c
#define RK808_LDO2_ON_VSEL_REG 0x3d
#define RK808_LDO2_SLP_VSEL_REG 0x3e
#define RK808_LDO3_ON_VSEL_REG 0x3f
#define RK808_LDO3_SLP_VSEL_REG 0x40
#define RK808_LDO4_ON_VSEL_REG 0x41
#define RK808_LDO4_SLP_VSEL_REG 0x42
#define RK808_LDO5_ON_VSEL_REG 0x43
#define RK808_LDO5_SLP_VSEL_REG 0x44
#define RK808_LDO6_ON_VSEL_REG 0x45
#define RK808_LDO6_SLP_VSEL_REG 0x46
#define RK808_LDO7_ON_VSEL_REG 0x47
#define RK808_LDO7_SLP_VSEL_REG 0x48
#define RK808_LDO8_ON_VSEL_REG 0x49
#define RK808_LDO8_SLP_VSEL_REG 0x4a
#define RK808_DEVCTRL_REG 0x4b
#define RK808_INT_STS_REG1 0x4c
#define RK808_INT_STS_MSK_REG1 0x4d
#define RK808_INT_STS_REG2 0x4e
#define RK808_INT_STS_MSK_REG2 0x4f
#define RK808_IO_POL_REG 0x50
/* IRQ Definitions */
#define RK808_IRQ_VOUT_LO 0
#define RK808_IRQ_VB_LO 1
#define RK808_IRQ_PWRON 2
#define RK808_IRQ_PWRON_LP 3
#define RK808_IRQ_HOTDIE 4
#define RK808_IRQ_RTC_ALARM 5
#define RK808_IRQ_RTC_PERIOD 6
#define RK808_IRQ_PLUG_IN_INT 7
#define RK808_IRQ_PLUG_OUT_INT 8
#define RK808_NUM_IRQ 9
#define RK808_IRQ_VOUT_LO_MSK BIT(0)
#define RK808_IRQ_VB_LO_MSK BIT(1)
#define RK808_IRQ_PWRON_MSK BIT(2)
#define RK808_IRQ_PWRON_LP_MSK BIT(3)
#define RK808_IRQ_HOTDIE_MSK BIT(4)
#define RK808_IRQ_RTC_ALARM_MSK BIT(5)
#define RK808_IRQ_RTC_PERIOD_MSK BIT(6)
#define RK808_IRQ_PLUG_IN_INT_MSK BIT(0)
#define RK808_IRQ_PLUG_OUT_INT_MSK BIT(1)
#define RK808_VBAT_LOW_2V8 0x00
#define RK808_VBAT_LOW_2V9 0x01
#define RK808_VBAT_LOW_3V0 0x02
#define RK808_VBAT_LOW_3V1 0x03
#define RK808_VBAT_LOW_3V2 0x04
#define RK808_VBAT_LOW_3V3 0x05
#define RK808_VBAT_LOW_3V4 0x06
#define RK808_VBAT_LOW_3V5 0x07
#define VBAT_LOW_VOL_MASK (0x07 << 0)
#define EN_VABT_LOW_SHUT_DOWN (0x00 << 4)
#define EN_VBAT_LOW_IRQ (0x1 << 4)
#define VBAT_LOW_ACT_MASK (0x1 << 4)
#define BUCK_ILMIN_MASK (7 << 0)
#define BOOST_ILMIN_MASK (7 << 0)
#define BUCK1_RATE_MASK (3 << 3)
#define BUCK2_RATE_MASK (3 << 3)
#define MASK_ALL 0xff
#define SWITCH2_EN BIT(6)
#define SWITCH1_EN BIT(5)
#define DEV_OFF_RST BIT(3)
#define VB_LO_ACT BIT(4)
#define VB_LO_SEL_3500MV (7 << 0)
#define VOUT_LO_INT BIT(0)
#define CLK32KOUT2_EN BIT(0)
enum {
BUCK_ILMIN_50MA,
BUCK_ILMIN_100MA,
BUCK_ILMIN_150MA,
BUCK_ILMIN_200MA,
BUCK_ILMIN_250MA,
BUCK_ILMIN_300MA,
BUCK_ILMIN_350MA,
BUCK_ILMIN_400MA,
};
enum {
BOOST_ILMIN_75MA,
BOOST_ILMIN_100MA,
BOOST_ILMIN_125MA,
BOOST_ILMIN_150MA,
BOOST_ILMIN_175MA,
BOOST_ILMIN_200MA,
BOOST_ILMIN_225MA,
BOOST_ILMIN_250MA,
};
struct rk808 {
struct i2c_client *i2c;
struct regmap_irq_chip_data *irq_data;
struct regmap *regmap;
};
#endif /* __LINUX_REGULATOR_rk808_H */
/*
* MFD core driver for Ricoh RN5T618 PMIC
*
* Copyright (C) 2014 Beniamino Galvani <b.galvani@gmail.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __LINUX_MFD_RN5T618_H
#define __LINUX_MFD_RN5T618_H
#include <linux/regmap.h>
#define RN5T618_LSIVER 0x00
#define RN5T618_OTPVER 0x01
#define RN5T618_IODAC 0x02
#define RN5T618_VINDAC 0x03
#define RN5T618_CPUCNT 0x06
#define RN5T618_PSWR 0x07
#define RN5T618_PONHIS 0x09
#define RN5T618_POFFHIS 0x0a
#define RN5T618_WATCHDOG 0x0b
#define RN5T618_WATCHDOGCNT 0x0c
#define RN5T618_PWRFUNC 0x0d
#define RN5T618_SLPCNT 0x0e
#define RN5T618_REPCNT 0x0f
#define RN5T618_PWRONTIMSET 0x10
#define RN5T618_NOETIMSETCNT 0x11
#define RN5T618_PWRIREN 0x12
#define RN5T618_PWRIRQ 0x13
#define RN5T618_PWRMON 0x14
#define RN5T618_PWRIRSEL 0x15
#define RN5T618_DC1_SLOT 0x16
#define RN5T618_DC2_SLOT 0x17
#define RN5T618_DC3_SLOT 0x18
#define RN5T618_LDO1_SLOT 0x1b
#define RN5T618_LDO2_SLOT 0x1c
#define RN5T618_LDO3_SLOT 0x1d
#define RN5T618_LDO4_SLOT 0x1e
#define RN5T618_LDO5_SLOT 0x1f
#define RN5T618_PSO0_SLOT 0x25
#define RN5T618_PSO1_SLOT 0x26
#define RN5T618_PSO2_SLOT 0x27
#define RN5T618_PSO3_SLOT 0x28
#define RN5T618_LDORTC1_SLOT 0x2a
#define RN5T618_DC1CTL 0x2c
#define RN5T618_DC1CTL2 0x2d
#define RN5T618_DC2CTL 0x2e
#define RN5T618_DC2CTL2 0x2f
#define RN5T618_DC3CTL 0x30
#define RN5T618_DC3CTL2 0x31
#define RN5T618_DC1DAC 0x36
#define RN5T618_DC2DAC 0x37
#define RN5T618_DC3DAC 0x38
#define RN5T618_DC1DAC_SLP 0x3b
#define RN5T618_DC2DAC_SLP 0x3c
#define RN5T618_DC3DAC_SLP 0x3d
#define RN5T618_DCIREN 0x40
#define RN5T618_DCIRQ 0x41
#define RN5T618_DCIRMON 0x42
#define RN5T618_LDOEN1 0x44
#define RN5T618_LDOEN2 0x45
#define RN5T618_LDODIS 0x46
#define RN5T618_LDO1DAC 0x4c
#define RN5T618_LDO2DAC 0x4d
#define RN5T618_LDO3DAC 0x4e
#define RN5T618_LDO4DAC 0x4f
#define RN5T618_LDO5DAC 0x50
#define RN5T618_LDORTCDAC 0x56
#define RN5T618_LDORTC2DAC 0x57
#define RN5T618_LDO1DAC_SLP 0x58
#define RN5T618_LDO2DAC_SLP 0x59
#define RN5T618_LDO3DAC_SLP 0x5a
#define RN5T618_LDO4DAC_SLP 0x5b
#define RN5T618_LDO5DAC_SLP 0x5c
#define RN5T618_ADCCNT1 0x64
#define RN5T618_ADCCNT2 0x65
#define RN5T618_ADCCNT3 0x66
#define RN5T618_ILIMDATAH 0x68
#define RN5T618_ILIMDATAL 0x69
#define RN5T618_VBATDATAH 0x6a
#define RN5T618_VBATDATAL 0x6b
#define RN5T618_VADPDATAH 0x6c
#define RN5T618_VADPDATAL 0x6d
#define RN5T618_VUSBDATAH 0x6e
#define RN5T618_VUSBDATAL 0x6f
#define RN5T618_VSYSDATAH 0x70
#define RN5T618_VSYSDATAL 0x71
#define RN5T618_VTHMDATAH 0x72
#define RN5T618_VTHMDATAL 0x73
#define RN5T618_AIN1DATAH 0x74
#define RN5T618_AIN1DATAL 0x75
#define RN5T618_AIN0DATAH 0x76
#define RN5T618_AIN0DATAL 0x77
#define RN5T618_ILIMTHL 0x78
#define RN5T618_ILIMTHH 0x79
#define RN5T618_VBATTHL 0x7a
#define RN5T618_VBATTHH 0x7b
#define RN5T618_VADPTHL 0x7c
#define RN5T618_VADPTHH 0x7d
#define RN5T618_VUSBTHL 0x7e
#define RN5T618_VUSBTHH 0x7f
#define RN5T618_VSYSTHL 0x80
#define RN5T618_VSYSTHH 0x81
#define RN5T618_VTHMTHL 0x82
#define RN5T618_VTHMTHH 0x83
#define RN5T618_AIN1THL 0x84
#define RN5T618_AIN1THH 0x85
#define RN5T618_AIN0THL 0x86
#define RN5T618_AIN0THH 0x87
#define RN5T618_EN_ADCIR1 0x88
#define RN5T618_EN_ADCIR2 0x89
#define RN5T618_EN_ADCIR3 0x8a
#define RN5T618_IR_ADC1 0x8c
#define RN5T618_IR_ADC2 0x8d
#define RN5T618_IR_ADC3 0x8e
#define RN5T618_IOSEL 0x90
#define RN5T618_IOOUT 0x91
#define RN5T618_GPEDGE1 0x92
#define RN5T618_GPEDGE2 0x93
#define RN5T618_EN_GPIR 0x94
#define RN5T618_IR_GPR 0x95
#define RN5T618_IR_GPF 0x96
#define RN5T618_MON_IOIN 0x97
#define RN5T618_GPLED_FUNC 0x98
#define RN5T618_INTPOL 0x9c
#define RN5T618_INTEN 0x9d
#define RN5T618_INTMON 0x9e
#define RN5T618_PREVINDAC 0xb0
#define RN5T618_BATDAC 0xb1
#define RN5T618_CHGCTL1 0xb3
#define RN5T618_CHGCTL2 0xb4
#define RN5T618_VSYSSET 0xb5
#define RN5T618_REGISET1 0xb6
#define RN5T618_REGISET2 0xb7
#define RN5T618_CHGISET 0xb8
#define RN5T618_TIMSET 0xb9
#define RN5T618_BATSET1 0xba
#define RN5T618_BATSET2 0xbb
#define RN5T618_DIESET 0xbc
#define RN5T618_CHGSTATE 0xbd
#define RN5T618_CHGCTRL_IRFMASK 0xbe
#define RN5T618_CHGSTAT_IRFMASK1 0xbf
#define RN5T618_CHGSTAT_IRFMASK2 0xc0
#define RN5T618_CHGERR_IRFMASK 0xc1
#define RN5T618_CHGCTRL_IRR 0xc2
#define RN5T618_CHGSTAT_IRR1 0xc3
#define RN5T618_CHGSTAT_IRR2 0xc4
#define RN5T618_CHGERR_IRR 0xc5
#define RN5T618_CHGCTRL_MONI 0xc6
#define RN5T618_CHGSTAT_MONI1 0xc7
#define RN5T618_CHGSTAT_MONI2 0xc8
#define RN5T618_CHGERR_MONI 0xc9
#define RN5T618_CHGCTRL_DETMOD1 0xca
#define RN5T618_CHGCTRL_DETMOD2 0xcb
#define RN5T618_CHGSTAT_DETMOD1 0xcc
#define RN5T618_CHGSTAT_DETMOD2 0xcd
#define RN5T618_CHGSTAT_DETMOD3 0xce
#define RN5T618_CHGERR_DETMOD1 0xcf
#define RN5T618_CHGERR_DETMOD2 0xd0
#define RN5T618_CHGOSCCTL 0xd4
#define RN5T618_CHGOSCSCORESET1 0xd5
#define RN5T618_CHGOSCSCORESET2 0xd6
#define RN5T618_CHGOSCSCORESET3 0xd7
#define RN5T618_CHGOSCFREQSET1 0xd8
#define RN5T618_CHGOSCFREQSET2 0xd9
#define RN5T618_CONTROL 0xe0
#define RN5T618_SOC 0xe1
#define RN5T618_RE_CAP_H 0xe2
#define RN5T618_RE_CAP_L 0xe3
#define RN5T618_FA_CAP_H 0xe4
#define RN5T618_FA_CAP_L 0xe5
#define RN5T618_AGE 0xe6
#define RN5T618_TT_EMPTY_H 0xe7
#define RN5T618_TT_EMPTY_L 0xe8
#define RN5T618_TT_FULL_H 0xe9
#define RN5T618_TT_FULL_L 0xea
#define RN5T618_VOLTAGE_1 0xeb
#define RN5T618_VOLTAGE_0 0xec
#define RN5T618_TEMP_1 0xed
#define RN5T618_TEMP_0 0xee
#define RN5T618_CC_CTRL 0xef
#define RN5T618_CC_COUNT2 0xf0
#define RN5T618_CC_COUNT1 0xf1
#define RN5T618_CC_COUNT0 0xf2
#define RN5T618_CC_SUMREG3 0xf3
#define RN5T618_CC_SUMREG2 0xf4
#define RN5T618_CC_SUMREG1 0xf5
#define RN5T618_CC_SUMREG0 0xf6
#define RN5T618_CC_OFFREG1 0xf7
#define RN5T618_CC_OFFREG0 0xf8
#define RN5T618_CC_GAINREG1 0xf9
#define RN5T618_CC_GAINREG0 0xfa
#define RN5T618_CC_AVEREG1 0xfb
#define RN5T618_CC_AVEREG0 0xfc
#define RN5T618_MAX_REG 0xfc
#define RN5T618_REPCNT_REPWRON BIT(0)
#define RN5T618_SLPCNT_SWPWROFF BIT(0)
#define RN5T618_WATCHDOG_WDOGEN BIT(2)
#define RN5T618_WATCHDOG_WDOGTIM_M (BIT(0) | BIT(1))
#define RN5T618_WATCHDOG_WDOGTIM_S 0
#define RN5T618_PWRIRQ_IR_WDOG BIT(6)
enum {
RN5T618_DCDC1,
RN5T618_DCDC2,
RN5T618_DCDC3,
RN5T618_LDO1,
RN5T618_LDO2,
RN5T618_LDO3,
RN5T618_LDO4,
RN5T618_LDO5,
RN5T618_LDORTC1,
RN5T618_LDORTC2,
RN5T618_REG_NUM,
};
struct rn5t618 {
struct regmap *regmap;
};
#endif /* __LINUX_MFD_RN5T618_H */
...@@ -155,6 +155,7 @@ struct ti_tscadc_dev { ...@@ -155,6 +155,7 @@ struct ti_tscadc_dev {
void __iomem *tscadc_base; void __iomem *tscadc_base;
int irq; int irq;
int used_cells; /* 1-2 */ int used_cells; /* 1-2 */
int tsc_wires;
int tsc_cell; /* -1 if not used */ int tsc_cell; /* -1 if not used */
int adc_cell; /* -1 if not used */ int adc_cell; /* -1 if not used */
struct mfd_cell cells[TSCADC_CELLS]; struct mfd_cell cells[TSCADC_CELLS];
......
/*
* Sequencer Serial Port (SSP) driver for Texas Instruments' SoCs
*
* Copyright (C) 2010 Texas Instruments Inc
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __TI_SSP_H__
#define __TI_SSP_H__
struct ti_ssp_dev_data {
const char *dev_name;
void *pdata;
size_t pdata_size;
};
struct ti_ssp_data {
unsigned long out_clock;
struct ti_ssp_dev_data dev_data[2];
};
struct ti_ssp_spi_data {
unsigned long iosel;
int num_cs;
void (*select)(int cs);
};
/*
* Sequencer port IO pin configuration bits. These do not correlate 1-1 with
* the hardware. The iosel field in the port data combines iosel1 and iosel2,
* and is therefore not a direct map to register space. It is best to use the
* macros below to construct iosel values.
*
* least significant 16 bits --> iosel1
* most significant 16 bits --> iosel2
*/
#define SSP_IN 0x0000
#define SSP_DATA 0x0001
#define SSP_CLOCK 0x0002
#define SSP_CHIPSEL 0x0003
#define SSP_OUT 0x0004
#define SSP_PIN_SEL(pin, v) ((v) << ((pin) * 3))
#define SSP_PIN_MASK(pin) SSP_PIN_SEL(pin, 0x7)
#define SSP_INPUT_SEL(pin) ((pin) << 16)
/* Sequencer port config bits */
#define SSP_EARLY_DIN BIT(8)
#define SSP_DELAY_DOUT BIT(9)
/* Sequence map definitions */
#define SSP_CLK_HIGH BIT(0)
#define SSP_CLK_LOW 0
#define SSP_DATA_HIGH BIT(1)
#define SSP_DATA_LOW 0
#define SSP_CS_HIGH BIT(2)
#define SSP_CS_LOW 0
#define SSP_OUT_MODE BIT(3)
#define SSP_IN_MODE 0
#define SSP_DATA_REG BIT(4)
#define SSP_ADDR_REG 0
#define SSP_OPCODE_DIRECT ((0x0) << 5)
#define SSP_OPCODE_TOGGLE ((0x1) << 5)
#define SSP_OPCODE_SHIFT ((0x2) << 5)
#define SSP_OPCODE_BRANCH0 ((0x4) << 5)
#define SSP_OPCODE_BRANCH1 ((0x5) << 5)
#define SSP_OPCODE_BRANCH ((0x6) << 5)
#define SSP_OPCODE_STOP ((0x7) << 5)
#define SSP_BRANCH(addr) ((addr) << 8)
#define SSP_COUNT(cycles) ((cycles) << 8)
int ti_ssp_raw_read(struct device *dev);
int ti_ssp_raw_write(struct device *dev, u32 val);
int ti_ssp_load(struct device *dev, int offs, u32* prog, int len);
int ti_ssp_run(struct device *dev, u32 pc, u32 input, u32 *output);
int ti_ssp_set_mode(struct device *dev, int mode);
int ti_ssp_set_iosel(struct device *dev, u32 iosel);
#endif /* __TI_SSP_H__ */
...@@ -60,6 +60,8 @@ ...@@ -60,6 +60,8 @@
#define TPS65217_REG_SEQ5 0X1D #define TPS65217_REG_SEQ5 0X1D
#define TPS65217_REG_SEQ6 0X1E #define TPS65217_REG_SEQ6 0X1E
#define TPS65217_REG_MAX TPS65217_REG_SEQ6
/* Register field definitions */ /* Register field definitions */
#define TPS65217_CHIPID_CHIP_MASK 0xF0 #define TPS65217_CHIPID_CHIP_MASK 0xF0
#define TPS65217_CHIPID_REV_MASK 0x0F #define TPS65217_CHIPID_REV_MASK 0x0F
......
...@@ -2560,6 +2560,7 @@ ...@@ -2560,6 +2560,7 @@
#define PCI_DEVICE_ID_INTEL_MFD_EMMC0 0x0823 #define PCI_DEVICE_ID_INTEL_MFD_EMMC0 0x0823
#define PCI_DEVICE_ID_INTEL_MFD_EMMC1 0x0824 #define PCI_DEVICE_ID_INTEL_MFD_EMMC1 0x0824
#define PCI_DEVICE_ID_INTEL_MRST_SD2 0x084F #define PCI_DEVICE_ID_INTEL_MRST_SD2 0x084F
#define PCI_DEVICE_ID_INTEL_QUARK_X1000_ILB 0x095E
#define PCI_DEVICE_ID_INTEL_I960 0x0960 #define PCI_DEVICE_ID_INTEL_I960 0x0960
#define PCI_DEVICE_ID_INTEL_I960RM 0x0962 #define PCI_DEVICE_ID_INTEL_I960RM 0x0962
#define PCI_DEVICE_ID_INTEL_CENTERTON_ILB 0x0c60 #define PCI_DEVICE_ID_INTEL_CENTERTON_ILB 0x0c60
......
...@@ -1220,7 +1220,7 @@ static int arizona_hw_params_rate(struct snd_pcm_substream *substream, ...@@ -1220,7 +1220,7 @@ static int arizona_hw_params_rate(struct snd_pcm_substream *substream,
break; break;
case ARIZONA_CLK_ASYNCCLK: case ARIZONA_CLK_ASYNCCLK:
snd_soc_update_bits(codec, ARIZONA_ASYNC_SAMPLE_RATE_1, snd_soc_update_bits(codec, ARIZONA_ASYNC_SAMPLE_RATE_1,
ARIZONA_ASYNC_SAMPLE_RATE_MASK, sr_val); ARIZONA_ASYNC_SAMPLE_RATE_1_MASK, sr_val);
if (base) if (base)
snd_soc_update_bits(codec, base + ARIZONA_AIF_RATE_CTRL, snd_soc_update_bits(codec, base + ARIZONA_AIF_RATE_CTRL,
ARIZONA_AIF1_RATE_MASK, ARIZONA_AIF1_RATE_MASK,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment