* [PATCH 06/10] iio: adc: stm32: add ext attrs to configure sampling time
From: Fabrice Gasnier @ 2016-10-25 16:25 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1477412722-24061-1-git-send-email-fabrice.gasnier@st.com>
Add per channel "smpr" IIO extended attribute, to allow sampling
time configuration.
Signed-off-by: Fabrice Gasnier <fabrice.gasnier@st.com>
---
drivers/iio/adc/stm32/stm32-adc.c | 75 +++++++++++++++++++++++++++++++++++++
drivers/iio/adc/stm32/stm32-adc.h | 25 +++++++++++++
drivers/iio/adc/stm32/stm32f4-adc.c | 48 ++++++++++++++++++++++++
3 files changed, 148 insertions(+)
diff --git a/drivers/iio/adc/stm32/stm32-adc.c b/drivers/iio/adc/stm32/stm32-adc.c
index 9b4b459..1681f75 100644
--- a/drivers/iio/adc/stm32/stm32-adc.c
+++ b/drivers/iio/adc/stm32/stm32-adc.c
@@ -38,6 +38,61 @@
#include "stm32-adc.h"
/**
+ * stm32_adc_conf_smp() - Configure sampling time for each channel
+ * @indio_dev: IIO device
+ * @scan_mask: channels to be converted
+ */
+static int stm32_adc_conf_smp(struct iio_dev *indio_dev,
+ const unsigned long *scan_mask)
+{
+ struct stm32_adc *adc = iio_priv(indio_dev);
+ const struct stm32_adc_regs *smp =
+ adc->common->data->adc_reginfo->smpr_regs;
+ struct stm32_adc_chan *stm32_chan;
+ const struct iio_chan_spec *chan;
+ u32 bit, val;
+ int i;
+
+ for_each_set_bit(bit, scan_mask, indio_dev->masklength) {
+ chan = indio_dev->channels + bit;
+ stm32_chan = to_stm32_chan(adc, chan);
+ i = chan->channel;
+
+ if (i >= adc->max_channels)
+ return -EINVAL;
+
+ val = stm32_adc_readl(adc, smp[i].reg);
+ val &= ~smp[i].mask;
+ val |= (stm32_chan->smpr << smp[i].shift) & smp[i].mask;
+ stm32_adc_writel(adc, smp[i].reg, val);
+ }
+
+ return 0;
+}
+
+int stm32_adc_set_smpr(struct iio_dev *indio_dev,
+ const struct iio_chan_spec *chan, unsigned int smpr)
+{
+ struct stm32_adc *adc = iio_priv(indio_dev);
+ struct stm32_adc_chan *stm32_chan = to_stm32_chan(adc, chan);
+
+ stm32_chan->smpr = smpr;
+
+ return 0;
+}
+EXPORT_SYMBOL_GPL(stm32_adc_set_smpr);
+
+int stm32_adc_get_smpr(struct iio_dev *indio_dev,
+ const struct iio_chan_spec *chan)
+{
+ struct stm32_adc *adc = iio_priv(indio_dev);
+ struct stm32_adc_chan *stm32_chan = to_stm32_chan(adc, chan);
+
+ return stm32_chan->smpr;
+}
+EXPORT_SYMBOL_GPL(stm32_adc_get_smpr);
+
+/**
* stm32_adc_conf_scan_seq() - Build regular or injected channels scan sequence
* @indio_dev: IIO device
* @scan_mask: channels to be converted
@@ -126,6 +181,12 @@ static int stm32_adc_conf_scan(struct iio_dev *indio_dev,
return ret;
}
+ ret = stm32_adc_conf_smp(indio_dev, scan_mask);
+ if (ret) {
+ dev_err(&indio_dev->dev, "Failed to configure samp time\n");
+ goto err_dis;
+ }
+
ret = stm32_adc_conf_scan_seq(indio_dev, scan_mask);
if (ret) {
dev_err(&indio_dev->dev, "Failed to configure sequence\n");
@@ -938,6 +999,7 @@ static int stm32_adc_chan_of_init(struct iio_dev *indio_dev,
const struct stm32_adc_info *adc_info)
{
struct stm32_adc *adc = iio_priv(indio_dev);
+ struct stm32_adc_common *common = adc->common;
struct device_node *node = indio_dev->dev.of_node;
struct property *prop;
const __be32 *cur;
@@ -945,6 +1007,19 @@ static int stm32_adc_chan_of_init(struct iio_dev *indio_dev,
int scan_index = 0, num_channels = 0;
u32 val;
+ if (!common->stm32_chans[adc->id]) {
+ /* Allocate extended attributes structure for an instance */
+ struct stm32_adc_chan *stm32_chans;
+
+ stm32_chans = devm_kcalloc(&indio_dev->dev,
+ adc_info->max_channels,
+ sizeof(*stm32_chans), GFP_KERNEL);
+ if (!stm32_chans)
+ return -ENOMEM;
+
+ common->stm32_chans[adc->id] = stm32_chans;
+ }
+
of_property_for_each_u32(node, "st,adc-channels", prop, cur, val)
num_channels++;
diff --git a/drivers/iio/adc/stm32/stm32-adc.h b/drivers/iio/adc/stm32/stm32-adc.h
index 6c9b70d..8cf1d5c 100644
--- a/drivers/iio/adc/stm32/stm32-adc.h
+++ b/drivers/iio/adc/stm32/stm32-adc.h
@@ -143,6 +143,14 @@ struct stm32_adc_chan_spec {
};
/**
+ * struct stm32_adc_chan - Extended specifications of stm32 adc channels
+ * @smpr: per channel sampling time selection
+ */
+struct stm32_adc_chan {
+ unsigned smpr:3;
+};
+
+/**
* struct stm32_adc_trig_info - ADC trigger info
* @extsel: trigger selection for regular or injected
* @name: name of the trigger, corresponding to its source
@@ -206,6 +214,7 @@ struct stm32_adc_trig_reginfo {
* @jdr: injected data registers offsets
* @sqr_regs: Regular sequence registers description
* @jsqr_reg: Injected sequence register description
+ * @smpr_regs: Sampling time registers description
* @trig_reginfo: regular trigger control registers description
* @jtrig_reginfo: injected trigger control registers description
*/
@@ -220,6 +229,7 @@ struct stm32_adc_reginfo {
u32 jdr[4];
const struct stm32_adc_regs *sqr_regs;
const struct stm32_adc_regs *jsqr_reg;
+ const struct stm32_adc_regs *smpr_regs;
const struct stm32_adc_trig_reginfo *trig_reginfo;
const struct stm32_adc_trig_reginfo *jtrig_reginfo;
};
@@ -328,6 +338,7 @@ struct stm32_adc {
* @aclk: common clock for the analog circuitry
* @vref: regulator reference
* @vref_mv: vref voltage (mv)
+ * @stm32_chans: stm32 channels extended specification data
* @gpio_descs: gpio descriptor used to configure EXTi triggers
* @lock: mutex
*/
@@ -341,11 +352,21 @@ struct stm32_adc_common {
struct clk *aclk;
struct regulator *vref;
int vref_mv;
+ struct stm32_adc_chan *stm32_chans[STM32_ADC_ID_MAX];
struct gpio_descs *gpios;
struct mutex lock; /* read_raw lock */
};
/* Helper routines */
+static inline struct stm32_adc_chan *to_stm32_chan(struct stm32_adc *adc,
+ const struct iio_chan_spec
+ *chan)
+{
+ struct stm32_adc_chan *stm32_chans = adc->common->stm32_chans[adc->id];
+
+ return &stm32_chans[chan->channel];
+}
+
static inline int stm32_adc_start_conv(struct stm32_adc *adc)
{
return adc->common->data->start_conv(adc);
@@ -458,6 +479,10 @@ static inline void stm32_adc_clr_bits(struct stm32_adc *adc, u32 reg, u32 bits)
/* STM32 common extended attributes */
extern const struct iio_enum stm32_adc_trig_pol;
+int stm32_adc_set_smpr(struct iio_dev *indio_dev,
+ const struct iio_chan_spec *chan, unsigned int smpr);
+int stm32_adc_get_smpr(struct iio_dev *indio_dev,
+ const struct iio_chan_spec *chan);
int stm32_adc_probe(struct platform_device *pdev);
int stm32_adc_remove(struct platform_device *pdev);
diff --git a/drivers/iio/adc/stm32/stm32f4-adc.c b/drivers/iio/adc/stm32/stm32f4-adc.c
index e033a68..e0e6211 100644
--- a/drivers/iio/adc/stm32/stm32f4-adc.c
+++ b/drivers/iio/adc/stm32/stm32f4-adc.c
@@ -330,6 +330,32 @@ enum stm32f4_adc_smpr {
};
/**
+ * stm32f4_smpr_regs[] - describe sampling time registers & bit fields
+ * Sorted so it can be indexed by channel number.
+ */
+static const struct stm32_adc_regs stm32f4_smpr_regs[] = {
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP0_MASK, STM32F4_SMP0_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP1_MASK, STM32F4_SMP1_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP2_MASK, STM32F4_SMP2_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP3_MASK, STM32F4_SMP3_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP4_MASK, STM32F4_SMP4_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP5_MASK, STM32F4_SMP5_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP6_MASK, STM32F4_SMP6_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP7_MASK, STM32F4_SMP7_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP8_MASK, STM32F4_SMP8_SHIFT },
+ { STM32F4_ADCX_SMPR2, STM32F4_SMP9_MASK, STM32F4_SMP9_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP10_MASK, STM32F4_SMP10_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP11_MASK, STM32F4_SMP11_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP12_MASK, STM32F4_SMP12_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP13_MASK, STM32F4_SMP13_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP14_MASK, STM32F4_SMP14_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP15_MASK, STM32F4_SMP15_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP16_MASK, STM32F4_SMP16_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP17_MASK, STM32F4_SMP17_SHIFT },
+ { STM32F4_ADCX_SMPR1, STM32F4_SMP18_MASK, STM32F4_SMP18_SHIFT },
+};
+
+/**
* stm32f4_sqr_regs - describe regular sequence registers
* - L: sequence len (register & bit field)
* - SQ1..SQ16: sequence entries (register & bit field)
@@ -407,6 +433,7 @@ enum stm32f4_adc_smpr {
},
.sqr_regs = stm32f4_sqr_regs,
.jsqr_reg = stm32f4_jsqr_reg,
+ .smpr_regs = stm32f4_smpr_regs,
.trig_reginfo = &stm32f4_adc_trig_reginfo,
.jtrig_reginfo = &stm32f4_adc_jtrig_reginfo,
};
@@ -555,7 +582,28 @@ static int stm32f4_adc_clk_sel(struct stm32_adc *adc)
return 0;
}
+/* stm32f4_smpr_items : Channel-wise programmable sampling time */
+static const char * const stm32f4_smpr_items[] = {
+ [STM32F4_SMPR_3_CK_CYCLES] = "3_cycles",
+ [STM32F4_SMPR_15_CK_CYCLES] = "15_cycles",
+ [STM32F4_SMPR_28_CK_CYCLES] = "28_cycles",
+ [STM32F4_SMPR_56_CK_CYCLES] = "56_cycles",
+ [STM32F4_SMPR_84_CK_CYCLES] = "84_cycles",
+ [STM32F4_SMPR_112_CK_CYCLES] = "112_cycles",
+ [STM32F4_SMPR_144_CK_CYCLES] = "144_cycles",
+ [STM32F4_SMPR_480_CK_CYCLES] = "480_cycles",
+};
+
+static const struct iio_enum stm32f4_smpr = {
+ .items = stm32f4_smpr_items,
+ .num_items = ARRAY_SIZE(stm32f4_smpr_items),
+ .get = stm32_adc_get_smpr,
+ .set = stm32_adc_set_smpr,
+};
+
static const struct iio_chan_spec_ext_info stm32f4_adc_ext_info[] = {
+ IIO_ENUM("smpr", IIO_SEPARATE, &stm32f4_smpr),
+ IIO_ENUM_AVAILABLE("smpr", &stm32f4_smpr),
IIO_ENUM("trigger_pol", IIO_SHARED_BY_ALL, &stm32_adc_trig_pol),
{
.name = "trigger_pol_available",
--
1.9.1
^ permalink raw reply related
* [PATCH 07/10] ARM: configs: stm32: enable IIO ADC driver
From: Fabrice Gasnier @ 2016-10-25 16:25 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1477412722-24061-1-git-send-email-fabrice.gasnier@st.com>
Signed-off-by: Fabrice Gasnier <fabrice.gasnier@st.com>
---
arch/arm/configs/stm32_defconfig | 2 ++
1 file changed, 2 insertions(+)
diff --git a/arch/arm/configs/stm32_defconfig b/arch/arm/configs/stm32_defconfig
index 1e5ec2a..5a5f50c 100644
--- a/arch/arm/configs/stm32_defconfig
+++ b/arch/arm/configs/stm32_defconfig
@@ -57,6 +57,8 @@ CONFIG_LEDS_TRIGGERS=y
CONFIG_LEDS_TRIGGER_HEARTBEAT=y
CONFIG_DMADEVICES=y
CONFIG_STM32_DMA=y
+CONFIG_IIO=y
+CONFIG_STM32F4_ADC=y
# CONFIG_FILE_LOCKING is not set
# CONFIG_DNOTIFY is not set
# CONFIG_INOTIFY_USER is not set
--
1.9.1
^ permalink raw reply related
* [PATCH 08/10] ARM: dts: stm32f429: Add adc support
From: Fabrice Gasnier @ 2016-10-25 16:25 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1477412722-24061-1-git-send-email-fabrice.gasnier@st.com>
Add adc support & pinctrl analog phandle (adc3_in8) to stm32f429.
Signed-off-by: Fabrice Gasnier <fabrice.gasnier@st.com>
---
arch/arm/boot/dts/stm32f429.dtsi | 62 ++++++++++++++++++++++++++++++++++++++++
1 file changed, 62 insertions(+)
diff --git a/arch/arm/boot/dts/stm32f429.dtsi b/arch/arm/boot/dts/stm32f429.dtsi
index 336ee4f..3fcd941 100644
--- a/arch/arm/boot/dts/stm32f429.dtsi
+++ b/arch/arm/boot/dts/stm32f429.dtsi
@@ -172,6 +172,62 @@
status = "disabled";
};
+ adc: adc at 40012000 {
+ compatible = "st,stm32f4-adc";
+ reg = <0x40012000 0x400>;
+ interrupts = <18>;
+ clocks = <&rcc 0 168>;
+ clock-names = "adc";
+ status = "disabled";
+
+ #address-cells = <1>;
+ #size-cells = <0>;
+ adc1: adc1-master at 0 {
+ #io-channel-cells = <1>;
+ reg = <0x0>;
+ clocks = <&rcc 0 168>;
+ status = "disabled";
+ };
+
+ jadc1: adc1-injected at 0 {
+ #io-channel-cells = <1>;
+ reg = <0x0>;
+ clocks = <&rcc 0 168>;
+ st,injected;
+ status = "disabled";
+ };
+
+ adc2: adc2-slave at 100 {
+ #io-channel-cells = <1>;
+ reg = <0x100>;
+ clocks = <&rcc 0 169>;
+ status = "disabled";
+ };
+
+ jadc2: adc2-injected at 100 {
+ #io-channel-cells = <1>;
+ reg = <0x100>;
+ clocks = <&rcc 0 169>;
+ st,injected;
+ status = "disabled";
+ };
+
+ adc3: adc3-slave at 200 {
+ #io-channel-cells = <1>;
+ reg = <0x200>;
+ clocks = <&rcc 0 170>;
+ status = "disabled";
+ };
+
+ jadc3: adc3-injected at 200 {
+ #io-channel-cells = <1>;
+ reg = <0x200>;
+ clocks = <&rcc 0 170>;
+ st,injected;
+ status = "disabled";
+ };
+ };
+
syscfg: system-config at 40013800 {
compatible = "syscon";
reg = <0x40013800 0x400>;
@@ -332,6 +388,12 @@
slew-rate = <2>;
};
};
+
+ adc3_in8_pin: adc at 0 {
+ pins {
+ pinmux = <STM32F429_PF10_FUNC_ANALOG>;
+ };
+ };
};
rcc: rcc at 40023810 {
--
1.9.1
^ permalink raw reply related
* [PATCH 09/10] ARM: dts: stm32f429: enable adc on eval board
From: Fabrice Gasnier @ 2016-10-25 16:25 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1477412722-24061-1-git-send-email-fabrice.gasnier@st.com>
Enable analog to digital converter on stm32f429i-eval board.
Signed-off-by: Fabrice Gasnier <fabrice.gasnier@st.com>
---
arch/arm/boot/dts/stm32429i-eval.dts | 30 ++++++++++++++++++++++++++++++
1 file changed, 30 insertions(+)
diff --git a/arch/arm/boot/dts/stm32429i-eval.dts b/arch/arm/boot/dts/stm32429i-eval.dts
index 6bfc595..0e8c900 100644
--- a/arch/arm/boot/dts/stm32429i-eval.dts
+++ b/arch/arm/boot/dts/stm32429i-eval.dts
@@ -65,6 +65,20 @@
serial0 = &usart1;
};
+ regulators {
+ compatible = "simple-bus";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ reg_vref: regulator at 0 {
+ compatible = "regulator-fixed";
+ reg = <0>;
+ regulator-name = "vref";
+ regulator-min-microvolt = <3300000>;
+ regulator-max-microvolt = <3300000>;
+ };
+ };
+
leds {
compatible = "gpio-leds";
green {
@@ -123,3 +137,19 @@
pinctrl-names = "default";
status = "okay";
};
+
+&adc {
+ pinctrl-names = "default";
+ pinctrl-0 = <&adc3_in8_pin>;
+ vref-supply = <®_vref>;
+ status = "okay";
+ adc3: adc3-slave at 200 {
+ st,adc-channels = <8>;
+ status = "okay";
+ };
+
+ jadc3: adc3-injected at 200 {
+ st,adc-channels = <8>;
+ status = "okay";
+ };
+};
--
1.9.1
^ permalink raw reply related
* [PATCH 10/10] ARM: dts: stm32f429: Add dma support to adc
From: Fabrice Gasnier @ 2016-10-25 16:25 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1477412722-24061-1-git-send-email-fabrice.gasnier@st.com>
Configure STM32 ADC to use dma by default.
Signed-off-by: Fabrice Gasnier <fabrice.gasnier@st.com>
---
arch/arm/boot/dts/stm32f429.dtsi | 6 ++++++
1 file changed, 6 insertions(+)
diff --git a/arch/arm/boot/dts/stm32f429.dtsi b/arch/arm/boot/dts/stm32f429.dtsi
index 3fcd941..a00f7a6 100644
--- a/arch/arm/boot/dts/stm32f429.dtsi
+++ b/arch/arm/boot/dts/stm32f429.dtsi
@@ -186,6 +186,8 @@
#io-channel-cells = <1>;
reg = <0x0>;
clocks = <&rcc 0 168>;
+ dmas = <&dma2 0 0 0x400 0x0>;
+ dma-names = "rx";
status = "disabled";
};
@@ -201,6 +203,8 @@
#io-channel-cells = <1>;
reg = <0x100>;
clocks = <&rcc 0 169>;
+ dmas = <&dma2 3 1 0x400 0x0>;
+ dma-names = "rx";
status = "disabled";
};
@@ -216,6 +220,8 @@
#io-channel-cells = <1>;
reg = <0x200>;
clocks = <&rcc 0 170>;
+ dmas = <&dma2 1 2 0x400 0x0>;
+ dma-names = "rx";
status = "disabled";
};
--
1.9.1
^ permalink raw reply related
* [PATCH] exynos-drm: Fix display manager failing to start without IOMMU problem
From: Shuah Khan @ 2016-10-25 16:37 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <49780a7f-59a4-d2b0-380c-4bd330660ba2@osg.samsung.com>
On 10/19/2016 04:27 PM, Shuah Khan wrote:
> On 10/19/2016 08:16 AM, Inki Dae wrote:
>> Hi Shuah,
>>
>> 2016-10-13 8:11 GMT+09:00 Shuah Khan <shuahkh@osg.samsung.com>:
>>> Hi Inki,
>>>
>>> On 08/15/2016 10:40 PM, Inki Dae wrote:
>>>
>>>>>
>>>>> okay the very first commit that added IOMMU support
>>>>> introduced the code that rejects non-contig gem memory
>>>>> type without IOMMU.
>>>>>
>>>>> commit 0519f9a12d0113caab78980c48a7902d2bd40c2c
>>>>> Author: Inki Dae <inki.dae@samsung.com>
>>>>> Date: Sat Oct 20 07:53:42 2012 -0700
>>>>>
>>>>> drm/exynos: add iommu support for exynos drm framework
>>>>>
>>>
>>> I haven't given up on this yet. I am still seeing the following failure:
>>>
>>> Additional debug messages I added:
>>> [ 15.287403] exynos_drm_gem_create_ioctl() 1
>>> [ 15.287419] exynos_drm_gem_create() flags 1
>>>
>>> [ 15.311511] [drm:exynos_drm_framebuffer_init] *ERROR* Non-contiguous GEM memory is not supported.
>>>
>>> Additional debug message I added:
>>> [ 15.318981] [drm:exynos_user_fb_create] *ERROR* failed to initialize framebuffer
>>>
>>> This is what happens:
>>>
>>> 1. exynos_drm_gem_create_ioctl() gets called with EXYNOS_BO_NONCONTIG request
>>> 2. exynos_drm_gem_create(0 goes ahead and creates the GEM buffers
>>> 3. exynos_user_fb_create() tries to associate GEM to fb and fails during
>>> check_fb_gem_memory_type()
>>>
>>> At this point, there is no recovery and lightdm fails
>>>
>>> xf86-video-armsoc/src/drmmode_exynos/drmmode_exynos.c assumes contiguous
>>> allocations are not supported in some exynos drm versions: The following
>>> commit introduced this change:
>>>
>>> https://git.linaro.org/arm/xorg/driver/xf86-video-armsoc.git/commitdiff/3be1f6273441fe95dd442f44064387322e16b7e9
>>>
>>> excerpts from the diff:- if (create_gem->buf_type == ARMSOC_BO_SCANOUT)
>>> - create_exynos.flags = EXYNOS_BO_CONTIG;
>>> - else
>>> - create_exynos.flags = EXYNOS_BO_NONCONTIG;
>>> +
>>> + /* Contiguous allocations are not supported in some exynos drm versions.
>>> + * When they are supported all allocations are effectively contiguous
>>> + * anyway, so for simplicity we always request non contiguous buffers.
>>> + */
>>> + create_exynos.flags = EXYNOS_BO_NONCONTIG;
>>>
>>
>> Above comment, "Contiguous allocations are not supported in some
>> exynos drm versions.", seems wrong assumption.
>> The root cause, contiguous allocation is not supported, would be that
>> they used Linux kernel which didn't have CMA region enough - as
>> default 16MB, or didn't declare CMA region enough for the DMA device.
>> So I think they should not force to flag EXYNOS_BO_NONCONTIG and they
>> should manage the error case if the allocation failed.
>
> This assumption doesn't sound correct and forcing NONCONTIG isn't right
> either.
>
>>
>>> There might have been logic on exynos_drm that forced Contig when it coudn't
>>> support NONCONTIG. At least, that is what this comment suggests. This assumption
>>> doesn't appear to be a good one and not sure if this change was made to fix a bug.
>>>
>>> After the IOMMU support, this assumption is no longer true. Hence, with IOMMU
>>> support, latest kernels have a mismatch with the installed xf86-video-armsoc
>>>
>>> This is what I am running into. This leads to the following question:
>>>
>>> 1. How do we ensure exynos_drm kernel changes don't break user-space
>>> specifically xf86-video-armsoc
>>> 2. This seems to have gone undetected for a while. I see a change in
>>> exynos_drm_gem_dumb_create() that is probably addressing this type
>>> of breakage. Commit 122beea84bb90236b1ae545f08267af58591c21b adds
>>> handling for IOMMU NONCONTIG case.
>>
>> Seems this patch has a problem. This patch forces to flag NONCONTIG if
>> iommu is enabled. The flag should be depend on the argument from
>> user-space.
>> I.e., if user-space requested a gem allocation with CONTIG flag, then
>> Exynos drm driver should allocate contiguous memory even though iommu
>> is enabled.
>>
>>>
>>> Anyway, I am interested in getting the exynos_drm kernel side code
>>> and xf86-video-armsoc in sync to resolve the issue.
>>>
>>> Could you recommend a going forward plan?
>>
>> My opinion are,
>>
>> 1. Do not force to flag EXYNOS_BO_NONCONTIG at xf86-video-armsoc
Okay more on this. I fixed xf86-video-armso to ask for EXYNOS_BO_CONTIG
for ARMSOC_BO_SCANOUT and EXYNOS_BO_NONCONTIG in all other cases.
Revert of the commit: 3be1f6273441fe95dd442f44064387322e16b7e9
With this change, now display manager starts just fine. However, it turns
out xf86-video-armsoc is obsoleted in favor of xf86-video-modesetting. The
last update to xf86-video-armsoc git was 3 years ago.
I am not sure where to send the fix and doesn't look like it is being
maintained actively. I can pursue it further and try to get this into
xf86-video-armsoc provided I can find the maintainer for this seemingly
inactive project.
I brought in the latest xf86-video-modesetting bits from
https://cgit.freedesktop.org/xorg/driver/xf86-video-modesetting
I removed xf86-video-armsoc and installed xf86-video-modesetting and that
worked just fine. xf86-video-modesetting uses dumb_create interface instead
of DRM_IOCTL_EXYNOS_GEM_CREATE.
dumb_create interface eliminates the need for DRM_IOCTL_EXYNOS_GEM_CREATE
in userspace. libdrm-2.4.71 does call DRM_IOCTL_EXYNOS_GEM_CREATE.
The question is do we still need to continue to support the custom gem
create interface DRM_IOCTL_EXYNOS_GEM_CREATE? Some drm drivers seem to
support it and some don't. Unfortunately, if userspace requests noncontig
for scanout, we will continue to see problems with display manager when
iommu is disabled. dumb create hides all of that, are there good reasons
to continue to support it in exynos drm?
Exposing CONTIG and NONCONTIG to userspace appears to be causing problems
when exynos drm determines it can't support non-contig GEM buffers in fb
init after userspace allocates them.
>> 2. Do not force to flag NONCONTIG at Exynos drm driver even though
>> iommu is enabled and flag allocation type with the argument from
>> user-space.
>>
exynos_drm_gem_dumb_create() doesn't take any flags, there is no need
to change the above.
thanks,
-- Shuah
^ permalink raw reply
* [PATCH V2] arm64: Neaten show_regs, remove KERN_CONT
From: Joe Perches @ 2016-10-25 16:40 UTC (permalink / raw)
To: linux-arm-kernel
commit db4b0710fae9 ("arm64: fix show_regs fallout from KERN_CONT changes")
corrected the KERN_CONT fallout from commit 4bcc595ccd80
("printk: reinstate KERN_CONT for printing continuation lines"), but
the code still has unnecessary KERN_CONT uses.
Remove the KERN_CONT uses to avoid possible message interleaving.
Miscellanea:
o Remove unnecessary trailing blank from the output too.
o Convert i and top_reg to unsigned int
o Move the extra blank line after __show_reg to the caller for symmetry
Signed-off-by: Joe Perches <joe@perches.com>
---
arch/arm64/kernel/process.c | 21 ++++++++++-----------
1 file changed, 10 insertions(+), 11 deletions(-)
diff --git a/arch/arm64/kernel/process.c b/arch/arm64/kernel/process.c
index 01753cd7d3f0..5ba12f019bf7 100644
--- a/arch/arm64/kernel/process.c
+++ b/arch/arm64/kernel/process.c
@@ -168,7 +168,7 @@ void machine_restart(char *cmd)
void __show_regs(struct pt_regs *regs)
{
- int i, top_reg;
+ unsigned int i, top_reg;
u64 lr, sp;
if (compat_user_mode(regs)) {
@@ -190,24 +190,23 @@ void __show_regs(struct pt_regs *regs)
i = top_reg;
- while (i >= 0) {
- printk("x%-2d: %016llx ", i, regs->regs[i]);
+ if (i % 2) {
+ printk("x%-2d: %016llx\n", i, regs->regs[i]);
i--;
-
- if (i % 2 == 0) {
- pr_cont("x%-2d: %016llx ", i, regs->regs[i]);
- i--;
- }
-
- pr_cont("\n");
}
- printk("\n");
+ while (i > 0) {
+ printk("x%-2d: %016llx x%-2d: %016llx\n",
+ i, regs->regs[i],
+ i - 1, regs->regs[i - 1]);
+ i -= 2;
+ }
}
void show_regs(struct pt_regs * regs)
{
printk("\n");
__show_regs(regs);
+ printk("\n");
}
static void tls_thread_flush(void)
--
2.10.0.rc2.1.g053435c
^ permalink raw reply related
* [PATCH] drm: convert DT component matching to component_match_add_release()
From: Sean Paul @ 2016-10-25 16:44 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <E1bwo6l-0005Io-Q1@rmk-PC.armlinux.org.uk>
On Wed, Oct 19, 2016 at 6:28 AM, Russell King
<rmk+kernel@armlinux.org.uk> wrote:
> Convert DT component matching to use component_match_add_release().
>
> Signed-off-by: Russell King <rmk+kernel@armlinux.org.uk>
Applied to drm-misc, thanks!
Sean
> ---
> Can we please get this patch from May merged into the drm-misc or
> whatever trees so that we don't end up with conflicts? I've no idea
> who looks after drm-misc, as they have _still_ failed to add
> themselves to MAINTAINERS.
>
> drivers/gpu/drm/arm/hdlcd_drv.c | 3 ++-
> drivers/gpu/drm/arm/malidp_drv.c | 4 +++-
> drivers/gpu/drm/armada/armada_drv.c | 2 +-
> drivers/gpu/drm/drm_of.c | 28 +++++++++++++++++++++++--
> drivers/gpu/drm/etnaviv/etnaviv_drv.c | 5 +++--
> drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c | 7 ++++---
> drivers/gpu/drm/mediatek/mtk_drm_drv.c | 4 +++-
> drivers/gpu/drm/msm/msm_drv.c | 12 ++++++-----
> drivers/gpu/drm/rockchip/rockchip_drm_drv.c | 6 ++++--
> drivers/gpu/drm/sti/sti_drv.c | 5 +++--
> drivers/gpu/drm/sun4i/sun4i_drv.c | 3 ++-
> drivers/gpu/drm/tilcdc/tilcdc_external.c | 4 +++-
> include/drm/drm_of.h | 12 +++++++++++
> 13 files changed, 73 insertions(+), 22 deletions(-)
>
> diff --git a/drivers/gpu/drm/arm/hdlcd_drv.c b/drivers/gpu/drm/arm/hdlcd_drv.c
> index fb6a418ce6be..6477d1a65266 100644
> --- a/drivers/gpu/drm/arm/hdlcd_drv.c
> +++ b/drivers/gpu/drm/arm/hdlcd_drv.c
> @@ -453,7 +453,8 @@ static int hdlcd_probe(struct platform_device *pdev)
> return -EAGAIN;
> }
>
> - component_match_add(&pdev->dev, &match, compare_dev, port);
> + drm_of_component_match_add(&pdev->dev, &match, compare_dev, port);
> + of_node_put(port);
>
> return component_master_add_with_match(&pdev->dev, &hdlcd_master_ops,
> match);
> diff --git a/drivers/gpu/drm/arm/malidp_drv.c b/drivers/gpu/drm/arm/malidp_drv.c
> index 9280358b8f15..9f4739452a25 100644
> --- a/drivers/gpu/drm/arm/malidp_drv.c
> +++ b/drivers/gpu/drm/arm/malidp_drv.c
> @@ -493,7 +493,9 @@ static int malidp_platform_probe(struct platform_device *pdev)
> return -EAGAIN;
> }
>
> - component_match_add(&pdev->dev, &match, malidp_compare_dev, port);
> + drm_of_component_match_add(&pdev->dev, &match, malidp_compare_dev,
> + port);
> + of_node_put(port);
> return component_master_add_with_match(&pdev->dev, &malidp_master_ops,
> match);
> }
> diff --git a/drivers/gpu/drm/armada/armada_drv.c b/drivers/gpu/drm/armada/armada_drv.c
> index 1e0e68f608e4..94e46da9a758 100644
> --- a/drivers/gpu/drm/armada/armada_drv.c
> +++ b/drivers/gpu/drm/armada/armada_drv.c
> @@ -254,7 +254,7 @@ static void armada_add_endpoints(struct device *dev,
> continue;
> }
>
> - component_match_add(dev, match, compare_of, remote);
> + drm_of_component_match_add(dev, match, compare_of, remote);
> of_node_put(remote);
> }
> }
> diff --git a/drivers/gpu/drm/drm_of.c b/drivers/gpu/drm/drm_of.c
> index bc98bb94264d..47848ed8ca48 100644
> --- a/drivers/gpu/drm/drm_of.c
> +++ b/drivers/gpu/drm/drm_of.c
> @@ -6,6 +6,11 @@
> #include <drm/drm_crtc.h>
> #include <drm/drm_of.h>
>
> +static void drm_release_of(struct device *dev, void *data)
> +{
> + of_node_put(data);
> +}
> +
> /**
> * drm_crtc_port_mask - find the mask of a registered CRTC by port OF node
> * @dev: DRM device
> @@ -64,6 +69,24 @@ uint32_t drm_of_find_possible_crtcs(struct drm_device *dev,
> EXPORT_SYMBOL(drm_of_find_possible_crtcs);
>
> /**
> + * drm_of_component_match_add - Add a component helper OF node match rule
> + * @master: master device
> + * @matchptr: component match pointer
> + * @compare: compare function used for matching component
> + * @node: of_node
> + */
> +void drm_of_component_match_add(struct device *master,
> + struct component_match **matchptr,
> + int (*compare)(struct device *, void *),
> + struct device_node *node)
> +{
> + of_node_get(node);
> + component_match_add_release(master, matchptr, drm_release_of,
> + compare, node);
> +}
> +EXPORT_SYMBOL_GPL(drm_of_component_match_add);
> +
> +/**
> * drm_of_component_probe - Generic probe function for a component based master
> * @dev: master device containing the OF node
> * @compare_of: compare function used for matching components
> @@ -101,7 +124,7 @@ int drm_of_component_probe(struct device *dev,
> continue;
> }
>
> - component_match_add(dev, &match, compare_of, port);
> + drm_of_component_match_add(dev, &match, compare_of, port);
> of_node_put(port);
> }
>
> @@ -140,7 +163,8 @@ int drm_of_component_probe(struct device *dev,
> continue;
> }
>
> - component_match_add(dev, &match, compare_of, remote);
> + drm_of_component_match_add(dev, &match, compare_of,
> + remote);
> of_node_put(remote);
> }
> of_node_put(port);
> diff --git a/drivers/gpu/drm/etnaviv/etnaviv_drv.c b/drivers/gpu/drm/etnaviv/etnaviv_drv.c
> index aa687669e22b..0dee6acbd880 100644
> --- a/drivers/gpu/drm/etnaviv/etnaviv_drv.c
> +++ b/drivers/gpu/drm/etnaviv/etnaviv_drv.c
> @@ -16,6 +16,7 @@
>
> #include <linux/component.h>
> #include <linux/of_platform.h>
> +#include <drm/drm_of.h>
>
> #include "etnaviv_drv.h"
> #include "etnaviv_gpu.h"
> @@ -629,8 +630,8 @@ static int etnaviv_pdev_probe(struct platform_device *pdev)
> if (!core_node)
> break;
>
> - component_match_add(&pdev->dev, &match, compare_of,
> - core_node);
> + drm_of_component_match_add(&pdev->dev, &match,
> + compare_of, core_node);
> of_node_put(core_node);
> }
> } else if (dev->platform_data) {
> diff --git a/drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c b/drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c
> index 90377a609c98..e88fde18c946 100644
> --- a/drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c
> +++ b/drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c
> @@ -24,6 +24,7 @@
> #include <drm/drm_fb_cma_helper.h>
> #include <drm/drm_atomic_helper.h>
> #include <drm/drm_crtc_helper.h>
> +#include <drm/drm_of.h>
>
> #include "kirin_drm_drv.h"
>
> @@ -260,14 +261,13 @@ static struct device_node *kirin_get_remote_node(struct device_node *np)
> DRM_ERROR("no valid endpoint node\n");
> return ERR_PTR(-ENODEV);
> }
> - of_node_put(endpoint);
>
> remote = of_graph_get_remote_port_parent(endpoint);
> + of_node_put(endpoint);
> if (!remote) {
> DRM_ERROR("no valid remote node\n");
> return ERR_PTR(-ENODEV);
> }
> - of_node_put(remote);
>
> if (!of_device_is_available(remote)) {
> DRM_ERROR("not available for remote node\n");
> @@ -294,7 +294,8 @@ static int kirin_drm_platform_probe(struct platform_device *pdev)
> if (IS_ERR(remote))
> return PTR_ERR(remote);
>
> - component_match_add(dev, &match, compare_of, remote);
> + drm_of_component_match_add(dev, &match, compare_of, remote);
> + of_node_put(remote);
>
> return component_master_add_with_match(dev, &kirin_drm_ops, match);
>
> diff --git a/drivers/gpu/drm/mediatek/mtk_drm_drv.c b/drivers/gpu/drm/mediatek/mtk_drm_drv.c
> index cf83f6507ec8..9c5430fb82a2 100644
> --- a/drivers/gpu/drm/mediatek/mtk_drm_drv.c
> +++ b/drivers/gpu/drm/mediatek/mtk_drm_drv.c
> @@ -18,6 +18,7 @@
> #include <drm/drm_crtc_helper.h>
> #include <drm/drm_gem.h>
> #include <drm/drm_gem_cma_helper.h>
> +#include <drm/drm_of.h>
> #include <linux/component.h>
> #include <linux/iommu.h>
> #include <linux/of_address.h>
> @@ -415,7 +416,8 @@ static int mtk_drm_probe(struct platform_device *pdev)
> comp_type == MTK_DPI) {
> dev_info(dev, "Adding component match for %s\n",
> node->full_name);
> - component_match_add(dev, &match, compare_of, node);
> + drm_of_component_match_add(dev, &match, compare_of,
> + node);
> } else {
> struct mtk_ddp_comp *comp;
>
> diff --git a/drivers/gpu/drm/msm/msm_drv.c b/drivers/gpu/drm/msm/msm_drv.c
> index fb5c0b0a7594..84d38eaea585 100644
> --- a/drivers/gpu/drm/msm/msm_drv.c
> +++ b/drivers/gpu/drm/msm/msm_drv.c
> @@ -15,6 +15,8 @@
> * this program. If not, see <http://www.gnu.org/licenses/>.
> */
>
> +#include <drm/drm_of.h>
> +
> #include "msm_drv.h"
> #include "msm_debugfs.h"
> #include "msm_fence.h"
> @@ -919,8 +921,8 @@ static int add_components_mdp(struct device *mdp_dev,
> continue;
> }
>
> - component_match_add(master_dev, matchptr, compare_of, intf);
> -
> + drm_of_component_match_add(master_dev, matchptr, compare_of,
> + intf);
> of_node_put(intf);
> of_node_put(ep_node);
> }
> @@ -962,8 +964,8 @@ static int add_display_components(struct device *dev,
> put_device(mdp_dev);
>
> /* add the MDP component itself */
> - component_match_add(dev, matchptr, compare_of,
> - mdp_dev->of_node);
> + drm_of_component_match_add(dev, matchptr, compare_of,
> + mdp_dev->of_node);
> } else {
> /* MDP4 */
> mdp_dev = dev;
> @@ -996,7 +998,7 @@ static int add_gpu_components(struct device *dev,
> if (!np)
> return 0;
>
> - component_match_add(dev, matchptr, compare_of, np);
> + drm_of_component_match_add(dev, matchptr, compare_of, np);
>
> of_node_put(np);
>
> diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_drv.c b/drivers/gpu/drm/rockchip/rockchip_drm_drv.c
> index 8c8cbe837e61..6fe161192bb4 100644
> --- a/drivers/gpu/drm/rockchip/rockchip_drm_drv.c
> +++ b/drivers/gpu/drm/rockchip/rockchip_drm_drv.c
> @@ -20,6 +20,7 @@
> #include <drm/drm_crtc_helper.h>
> #include <drm/drm_fb_helper.h>
> #include <drm/drm_gem_cma_helper.h>
> +#include <drm/drm_of.h>
> #include <linux/dma-mapping.h>
> #include <linux/pm_runtime.h>
> #include <linux/module.h>
> @@ -388,7 +389,7 @@ static void rockchip_add_endpoints(struct device *dev,
> continue;
> }
>
> - component_match_add(dev, match, compare_of, remote);
> + drm_of_component_match_add(dev, match, compare_of, remote);
> of_node_put(remote);
> }
> }
> @@ -437,7 +438,8 @@ static int rockchip_drm_platform_probe(struct platform_device *pdev)
> }
>
> of_node_put(iommu);
> - component_match_add(dev, &match, compare_of, port->parent);
> + drm_of_component_match_add(dev, &match, compare_of,
> + port->parent);
> of_node_put(port);
> }
>
> diff --git a/drivers/gpu/drm/sti/sti_drv.c b/drivers/gpu/drm/sti/sti_drv.c
> index 2784919a7366..5e819876e642 100644
> --- a/drivers/gpu/drm/sti/sti_drv.c
> +++ b/drivers/gpu/drm/sti/sti_drv.c
> @@ -17,6 +17,7 @@
> #include <drm/drm_crtc_helper.h>
> #include <drm/drm_gem_cma_helper.h>
> #include <drm/drm_fb_cma_helper.h>
> +#include <drm/drm_of.h>
>
> #include "sti_crtc.h"
> #include "sti_drv.h"
> @@ -423,8 +424,8 @@ static int sti_platform_probe(struct platform_device *pdev)
> child_np = of_get_next_available_child(node, NULL);
>
> while (child_np) {
> - component_match_add(dev, &match, compare_of, child_np);
> - of_node_put(child_np);
> + drm_of_component_match_add(dev, &match, compare_of,
> + child_np);
> child_np = of_get_next_available_child(node, child_np);
> }
>
> diff --git a/drivers/gpu/drm/sun4i/sun4i_drv.c b/drivers/gpu/drm/sun4i/sun4i_drv.c
> index 0da9862ad8ed..b3c4ad605e81 100644
> --- a/drivers/gpu/drm/sun4i/sun4i_drv.c
> +++ b/drivers/gpu/drm/sun4i/sun4i_drv.c
> @@ -18,6 +18,7 @@
> #include <drm/drm_fb_cma_helper.h>
> #include <drm/drm_gem_cma_helper.h>
> #include <drm/drm_fb_helper.h>
> +#include <drm/drm_of.h>
>
> #include "sun4i_crtc.h"
> #include "sun4i_drv.h"
> @@ -239,7 +240,7 @@ static int sun4i_drv_add_endpoints(struct device *dev,
> /* Add current component */
> DRM_DEBUG_DRIVER("Adding component %s\n",
> of_node_full_name(node));
> - component_match_add(dev, match, compare_of, node);
> + drm_of_component_match_add(dev, match, compare_of, node);
> count++;
> }
>
> diff --git a/drivers/gpu/drm/tilcdc/tilcdc_external.c b/drivers/gpu/drm/tilcdc/tilcdc_external.c
> index 68e895021005..06a4c584f3cb 100644
> --- a/drivers/gpu/drm/tilcdc/tilcdc_external.c
> +++ b/drivers/gpu/drm/tilcdc/tilcdc_external.c
> @@ -10,6 +10,7 @@
>
> #include <linux/component.h>
> #include <linux/of_graph.h>
> +#include <drm/drm_of.h>
>
> #include "tilcdc_drv.h"
> #include "tilcdc_external.h"
> @@ -160,7 +161,8 @@ int tilcdc_get_external_components(struct device *dev,
>
> dev_dbg(dev, "Subdevice node '%s' found\n", node->name);
> if (match)
> - component_match_add(dev, match, dev_match_of, node);
> + drm_of_component_match_add(dev, match, dev_match_of,
> + node);
> of_node_put(node);
> count++;
> }
> diff --git a/include/drm/drm_of.h b/include/drm/drm_of.h
> index 3fd87b386ed7..d6b4c5587bbe 100644
> --- a/include/drm/drm_of.h
> +++ b/include/drm/drm_of.h
> @@ -4,6 +4,7 @@
> #include <linux/of_graph.h>
>
> struct component_master_ops;
> +struct component_match;
> struct device;
> struct drm_device;
> struct drm_encoder;
> @@ -12,6 +13,10 @@ struct device_node;
> #ifdef CONFIG_OF
> extern uint32_t drm_of_find_possible_crtcs(struct drm_device *dev,
> struct device_node *port);
> +extern void drm_of_component_match_add(struct device *master,
> + struct component_match **matchptr,
> + int (*compare)(struct device *, void *),
> + struct device_node *node);
> extern int drm_of_component_probe(struct device *dev,
> int (*compare_of)(struct device *, void *),
> const struct component_master_ops *m_ops);
> @@ -25,6 +30,13 @@ static inline uint32_t drm_of_find_possible_crtcs(struct drm_device *dev,
> return 0;
> }
>
> +static void drm_of_component_match_add(struct device *master,
> + struct component_match **matchptr,
> + int (*compare)(struct device *, void *),
> + struct device_node *node)
> +{
> +}
> +
> static inline int
> drm_of_component_probe(struct device *dev,
> int (*compare_of)(struct device *, void *),
> --
> 2.1.0
>
>
> _______________________________________________
> linux-arm-kernel mailing list
> linux-arm-kernel at lists.infradead.org
> http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
^ permalink raw reply
* [PATCH] arm64: Neaten show_regs, remove KERN_CONT
From: Joe Perches @ 2016-10-25 16:44 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161025143237.GD8898@leverpostej>
(adding Linus Torvalds)
On Tue, 2016-10-25 at 15:32 +0100, Mark Rutland wrote:
> On Mon, Oct 24, 2016 at 09:27:57AM -0700, Joe Perches wrote:
> > On Mon, 2016-10-24 at 12:31 +0100, Mark Rutland wrote:
> > > On Sun, Oct 23, 2016 at 01:40:49PM -0700, Joe Perches wrote:
> > > > commit db4b0710fae9 ("arm64: fix show_regs fallout from KERN_CONT changes")
> > > > corrected the KERN_CONT fallout from commit 4bcc595ccd80
> > > > ("printk: reinstate KERN_CONT for printing continuation lines"), but
> > > > the code still has unnecessary KERN_CONT uses. Remove them.
> > >
> > > Why are these unnecessary KERN_CONTs a larger problem than duplicating
> > > the format string for a third time? Having to duplicate it at all was
> > > annoying enough.
> >
> > Not printing partial lines is the best solution to avoiding
> > message output interleaving.
>
> Looking further, it seems that KERN_CONT is terminally broken. The core
> code somehow swallows newlines from some KERN_CONT prints in a
> non-deterministic fashion, and also appears to insert newlines from thin
> air. This happens in the absence of intervening printks.
>
> With the current code in v4.9-rc2, we get output like:
>
> x29: 0000ffffe4938c80 x28: 0000000000000000
> x27: 0000000000000000 x26: 0000000000000000 x25: 0000000000000000 x24: 0000000000000000
> x23: 0000000000000000 x22: 0000000000000000
> x21: 0000000000400470 x20: 0000000000000000
> x19: 0000000000000000 x18: 0000ffffe4938b60
> x17: 0000000000411000 x16: 0000ffff82f72c9c
> x15: 0000ffff830c8000 x14: 0000000000000040
> x13: 0000ffff830c8028 x12: 0000000000008738
> x11: 0000000000000008
> x10: 00000000ffffffff
> x9 : 0000ffff830b4e40 x8 : 2f2f2f2f2f2f2f2f
> x7 : b3b3bab7acff8b8a x6 : 0000ffff83097aa8
> x5 : 54d58839205d3679 x4 : 0000000000000000
> x3 : 00000000004005d0 x2 : ffff000000000000
> x1 : 0000ffffe4938e08 x0 : ffff000000000000
>
> ... or:
>
> x29: 0000fffff6f6a600 x28: 0000000000000000 x27: 0000000000000000 x26: 0000000000000000 x25: 0000000000000000 x24: 0000000000000000 x23: 0000000000000000 x22: 0000000000000000 x21: 0000000000400470 x20: 0000000000000000 x19: 0000000000000000 x18: 0000fffff6f6a4e0 x17: 0000000000411000 x16: 0000ffffa6e1fc9c x15: 0000ffffa6f75000 x14: 0000000000000040
> x13: 0000ffffa6f75028 x12: 0000000000008738 x11: 0000000000000008 x10: 00000000ffffffff
> x9 : 0000ffffa6f61e40 x8 : 2f2f2f2f2f2f2f2f x7 : b3b3bab7acff8b8a x6 : 0000ffffa6f44aa8
> x5 : 874b6ebb9d5e2f3d x4 : 0000000000000000 x3 : 00000000004005d0 x2 : ffff000000000000
> x1 : 0000fffff6f6a788 x0 : ffff000000000000
>
> ... and of course, the buffer shown by $(dmesg) or $(demsg -T) is equally
> insane, but different.
>
> I found that adding a space prior to newlines prevented them from being
> swallowed, but $(dmesg) would still suffer from random additions.
>
> Given all that, unless the core code is changed to as to behave
> deterministically at least for trivial cases like this one, I think we
> should avoid KERN_CONT like the plague.
>
> So FWIW, so long as you fold in the changes I requested in my other
> reply, please add:
>
> Acked-by: Mark Rutland <mark.rutland@arm.com>
>
> ... I'll go fix up show_pte() without pr_cont().
>
> Thanks,
> Mark.
^ permalink raw reply
* [PATCH 2/2] arm64: Support systems without FP/ASIMD
From: Suzuki K Poulose @ 2016-10-25 16:48 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CAKv+Gu9mzX5dUgkJzDYEwxP+u9RVL=RWdsPepQ-UeCCxpx1j_g@mail.gmail.com>
On 25/10/16 15:00, Ard Biesheuvel wrote:
> Hi Suzuki,
>
> On 25 October 2016 at 14:50, Suzuki K Poulose <suzuki.poulose@arm.com> wrote:
>> The arm64 kernel assumes that FP/ASIMD units are always present
>> and accesses the FP/ASIMD specific registers unconditionally. This
>> could cause problems when they are absent. This patch adds the
>> support for kernel handling systems without FP/ASIMD by skipping the
>> register access within the kernel. For kvm, we trap the accesses
>> to FP/ASIMD and inject an undefined instruction exception to the VM.
>>
>> The callers of the exported kernel_neon_begin_parital() should
>> make sure that the FP/ASIMD is supported.
>>
>> Cc: Catalin Marinas <catalin.marinas@arm.com>
>> Cc: Will Deacon <will.deacon@arm.com>
>> Cc: Christoffer Dall <christoffer.dall@linaro.org>
>> Cc: Marc Zyngier <marc.zyngier@arm.com>
>> Cc: Ard Biesheuvel <ard.biesheuvel@linaro.org>
>> Signed-off-by: Suzuki K Poulose <suzuki.poulose@arm.com>
>> ---
>> ---
>> arch/arm64/crypto/aes-ce-ccm-glue.c | 2 +-
>> arch/arm64/crypto/aes-ce-cipher.c | 2 ++
>> arch/arm64/crypto/ghash-ce-glue.c | 2 ++
>> arch/arm64/crypto/sha1-ce-glue.c | 2 ++
>> arch/arm64/include/asm/cpufeature.h | 8 +++++++-
>> arch/arm64/include/asm/neon.h | 3 ++-
>> arch/arm64/kernel/cpufeature.c | 15 +++++++++++++++
>> arch/arm64/kernel/fpsimd.c | 14 ++++++++++++++
>> arch/arm64/kvm/handle_exit.c | 11 +++++++++++
>> arch/arm64/kvm/hyp/hyp-entry.S | 9 ++++++++-
>> arch/arm64/kvm/hyp/switch.c | 5 ++++-
>> 11 files changed, 68 insertions(+), 5 deletions(-)
>>
>> diff --git a/arch/arm64/crypto/aes-ce-ccm-glue.c b/arch/arm64/crypto/aes-ce-ccm-glue.c
>> index f4bf2f2..d001b4e 100644
>> --- a/arch/arm64/crypto/aes-ce-ccm-glue.c
>> +++ b/arch/arm64/crypto/aes-ce-ccm-glue.c
>> @@ -296,7 +296,7 @@ static struct aead_alg ccm_aes_alg = {
>>
>> static int __init aes_mod_init(void)
>> {
>> - if (!(elf_hwcap & HWCAP_AES))
>> + if (!(elf_hwcap & HWCAP_AES) || !system_supports_fpsimd())
>
> This looks weird to me. All crypto extensionsinstructions except CRC
> operate strictly on FP/ASIMD registers, and so support for FP/ASIMD is
> implied by having HWCAP_AES. In other words, I think it makes more
> sense to sanity check that the info registers are consistent with each
> other in core code than modifying each user (which for HWCAP_xxx
> includes userland) to double check that the world is sane.
You're right. I will respin it.
Btw, I think we need the following feature check for the above. I will send
that in and remove the explicit HWCAP_AES check.
module_cpu_feature_match(AES, aes_mod_init());
Cheers
Suzuki
IMPORTANT NOTICE: The contents of this email and any attachments are confidential and may also be privileged. If you are not the intended recipient, please notify the sender immediately and do not disclose the contents to any other person, use it for any purpose, or store or copy the information in any medium. Thank you.
^ permalink raw reply
* [PATCH 3/4] dt-bindings: Update domain-idle-state binding to use correct compatibles
From: Sudeep Holla @ 2016-10-25 16:52 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161025162440.GA48977@linaro.org>
On 25/10/16 17:24, Lina Iyer wrote:
> On Tue, Oct 25 2016 at 09:59 -0600, Sudeep Holla wrote:
>>
>>
>> On 25/10/16 16:26, Lina Iyer wrote:
>>> Update domain-idle-state binding to use "domain-idle-state" compatible
>>> from Documentation/devicetree/bindings/arm/idle-states.txt.
>>>
>>> Cc: <devicetree@vger.kernel.org>
>>> Cc: Rob Herring <robh@kernel.org>
>>> Suggested-by: Sudeep Holla <sudeep.holla@arm.com>
>>> Signed-off-by: Lina Iyer <lina.iyer@linaro.org>
>>> ---
>>> Documentation/devicetree/bindings/power/power_domain.txt | 9 +++++----
>>> 1 file changed, 5 insertions(+), 4 deletions(-)
>>>
>>> diff --git a/Documentation/devicetree/bindings/power/power_domain.txt
>>> b/Documentation/devicetree/bindings/power/power_domain.txt
>>> index e165036..6fb53a3 100644
>>> --- a/Documentation/devicetree/bindings/power/power_domain.txt
>>> +++ b/Documentation/devicetree/bindings/power/power_domain.txt
>>> @@ -30,8 +30,9 @@ Optional properties:
>>> available in the next section.
>>>
>>> - domain-idle-states : A phandle of an idle-state that shall be
>>> soaked into a
>>> - generic domain power state. The idle state
>>> definitions are
>>> - compatible with arm,idle-state specified in [1].
>>> + generic domain power state. The idle state
>>> definitions must be
>>> + compatible with "domain-idle-state"
>>
>> I would reword the below a bit different so that it's flexible to be
>> reused without "arm,idle-state".
>>
>>> as well as
>>> + "arm,idle-state" as defined in [1].
>>
>> 'Idle states that are "arm,idle-state" compatible are generally
>> "domain-idle-state" compatible as well if it's a PM domain.'
>>
> I believe we should have both compatible strings. Per [1], any CPU that
> follows the idle state compatible *must* have "arm,idle-state" as a
> compatible.
Yes that's implicit for a CPU device. But generic power domain bindings
should not have that explicitly as it *can be* used for non CPU device.
> Since we are re-using the same compatible, its only correct
> that we retain what is already spec'd up in [1] and in addition provide
> this new compatible.
>
Yes [1] applies for *CPUs only* while this applies for *any device* and
*any power domain*, so I would drop *must have* "arm,idle-state" here
to keep this generic based on my understanding on how compatibles work.
--
Regards,
Sudeep
^ permalink raw reply
* [PATCH/RFT v2 12/17] USB: ochi-da8xx: Use a regulator for vbus/overcurrent
From: David Lechner @ 2016-10-25 16:53 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CAKXjFTOxQ58rThpPw9t73k-BBZ8YKGvMhWfAG1r+3kC=GJVxWg@mail.gmail.com>
On 10/25/2016 03:24 AM, Axel Haslam wrote:
> On Tue, Oct 25, 2016 at 3:39 AM, David Lechner <david@lechnology.com> wrote:
>> On 10/24/2016 11:46 AM, ahaslam at baylibre.com wrote:
>>>
>>> From: Axel Haslam <ahaslam@baylibre.com>
>>>
>>> Currently, the da8xx ohci driver uses a set of gpios and callbacks in
>>> board files to handle vbus and overcurrent irqs form the power supply.
>>> However, this does not play nice when moving to a DT based boot were
>>> we wont have board files.
>>>
>>> Instead of requesting and handling the gpio, use the regulator framework
>>> to take care of enabling and disabling vbus power.
>>> This has the benefit
>>> that we dont need to pass any more platform data to the driver:
>>>
>>> These will be handled by the regulator framework:
>>> set_power -> regulator_enable/regulator_disable
>>> get_power -> regulator_is_enabled
>>> get_oci -> regulator_get_mode
>>> ocic_notify -> regulator notification
>>>
>>> We can keep the default potpgt and use the regulator start delay instead:
>>> potpgt -> regulator startup delay time
>>>
>>> The hawk board does not have a GPIO/OVERCURRENT gpio to control vbus,
>>> (they should not have been decleared/reserved) so, just remove those
>>> definitions from the hwk board file.
>>>
>>> Signed-off-by: Axel Haslam <ahaslam@baylibre.com>
>>> ---
>>
>>
>>
>> How do you recover after an overcurrent event?
>>
>> I have configured a fixed-regulator using device-tree, but similar to the
>> configuration in the board files here. However, when I shorted out the VBUS
>> and caused an overcurrent event, I see nothing in the kernel log saying that
>> there was an overcurrent event and after I remove the short, the regulator
>> is never turned back on.
>>
>>
>
> You should have the patch to fix gpiolib, and you should declare the
> over current gpio on the regulator as such:
> (if the pin is enabled high you should add oc-active-high);
>
> vbus_fixed: fixed-regulator-vbus {
> compatible = "regulator-fixed";
> gpio = <&gpio 109 0>;
> oc-gpio = <&gpio 36 0>;
> regulator-boot-on;
> enable-active-high;
> regulator-name = "vbus";
> regulator-min-microvolt = <5000000>;
> regulator-max-microvolt = <5000000>;
> };
>
>
> Question: Do you see that the over current gpio was requested
> in debugfs/gpio? and, do you see the interrupt in /proc/interrupts?
>
> If you unplug and plug in back the usb device it should work again.
> also you can unbind and bind it should also start to work:
> something like:
>
> echo usb1 >/sys/bus/usb/drivers/usb/unbind
> echo usb1 >/sys/bus/usb/drivers/usb/bind
>
>
I have added oc-active-high and I get different results, but it is still
not quite right. When I short the VBUS, I can see that my overcurrent
gpio changes state. However, the driver does not turn of the VBUS. When
I remove the short, I get an overcurrent error in the kernel log. I
would expect this when I create the short, not when I remove it. I also
tried adding GPIO_ACTIVE_LOW to the oc-gpio, but this did not change
the behavior. In either case, the oc_gpio shows as high under normal
conditions, so perhaps there is a problem with the gpio-davinci driver
not picking up GPIO_ACTIVE_LOW from the device tree.
My regulator is basically the same. My device just uses different gpios.
vbus_reg: vbus-reg {
compatible = "regulator-fixed";
pinctrl-names = "default";
pinctrl-0 = <&usb11_pins>;
gpio = <&gpio 101 GPIO_ACTIVE_LOW>;
oc-gpio = <&gpio 99 0>;
enable-active-high;
oc-active-high;
regulator-name = "vbus";
regulator-min-microvolt = <5000000>;
regulator-max-microvolt = <5000000>;
}
It seems to me though that I should not have oc-active-high since under
normal conditions, the oc_gpio is high and during an overcurrent event,
the oc_gpio is low. Double-checking the behavior without oc-active-high,
I see that the vbus gpio is turned off in response to the overcurrent
event, but I don't get the overcurrent message in the kernel log.
Perhaps this is because as soon as there is an overcurrent event the
vbus turns off and the oc_gpio returns to normal before the usb driver
has a chance to poll the overcurrent state?
Also, unplugging the device and plugging it back in does nothing.
Unbinding and binding the driver does work, but that does not seem like
a very nice way to have to recover from an overcurrent event.
^ permalink raw reply
* [PATCH v2 0/4] ARM: K2G: Add support for TI-SCI Generic PM Domains
From: Kevin Hilman @ 2016-10-25 17:02 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161019203347.17893-1-d-gerlach@ti.com>
Dave Gerlach <d-gerlach@ti.com> writes:
> Hi,
> This is v2 of the series to add support for TI SCI PM Domains. v1 of
> the series can be found here [1]. Several things have changed since v1:
>
> - New patch to add a void *data to struct generic_pm_domain_data to
> allow to store per device data associated with a genpd
> - From v1, squash patch 1 and 2 to introduce docs and dt-bindings in
> one patch based on comment from Ulf
> - Fix some grammar errors in Documentation
> - Based on comments from Ulf, rework actual genpd implementation to
> avoid creating one genpd per device and instead use device start/stop
> hooks provided as part of genpd to control device state based on pm_runtime
> implementation. Also make use of new of_genpd_add_provider_simple API
> introduced by Jon Hunter and do not provide custom of_xlate to genpd core,
> instead registering devices as they probe through attach_dev hook provided
> by genpd framework.
>
> Most of the changes were motivated by the comments from Ulf Hannson on v1 that we
> should not use a 1-to-1 genpd to device mapping. The new approach allows us to
> create a single genpd and store information about each device as they attach to
> the genpd. Then the device start/stop hooks for that genpd leverage the
> per-device data to control power states over the TI SCI protocol.
>
> This driver makes use of the ti_sci driver sent here [2] by Nishanth Menon and
> applies on top of his series on v4.9-rc1.
Reviewed-by: Kevin Hilman <khilman@baylibre.com>
^ permalink raw reply
* [PATCH 2/3] ARM: convert to generated system call tables
From: Richard Henderson @ 2016-10-25 17:03 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <4146248.jXuviLlvH5@wuerfel>
On 10/25/2016 03:28 AM, Arnd Bergmann wrote:
> On Tuesday, October 25, 2016 10:12:10 PM CEST Michael Cree wrote:
>> On Fri, Oct 21, 2016 at 03:06:45PM +0200, Arnd Bergmann wrote:
>>> I see your point, but I think there are serious issues with the current
>>> approach as well:
>>>
>>> - a lot of the less common architectures just don't get updated
>>> in time, out of 22 architectures that don't use asm-generic/unistd.h,
>>> only 12 have pwritev2 in linux-next, and only three have pkey_mprotect
>>>
>>> - some architectures that add all syscalls sometimes make a mistake
>>> and forget one, e.g. alpha apparently never added __NR_bpf, but it
>>> did add the later __NR_execveat.
>>
>> __NR_bpf was not forgotten on Alpha. It was not wired up because
>> extra architecture support is needed which has not been implemented.
>>
>> But maybe we should just wire it up to sys_ni_syscall in the meantime
>> so a syscall number is reserved for it, and user space can call it to
>> get -ENOSYS returned.
>
> Ah, I must have misinterpreted the code then. I assumed that the
> bpf syscall always works on all architectures, but that only the
> jit compiler for it required architecture specific code to make it
> more efficient.
That was my interpretation as well. What's the problem, Michael?
r~
^ permalink raw reply
* [PATCH V2] arm64: Neaten show_regs, remove KERN_CONT
From: Mark Rutland @ 2016-10-25 17:07 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <289fb30081aba03fec0c960e7334f707bf36c881.1477413522.git.joe@perches.com>
On Tue, Oct 25, 2016 at 09:40:26AM -0700, Joe Perches wrote:
> commit db4b0710fae9 ("arm64: fix show_regs fallout from KERN_CONT changes")
> corrected the KERN_CONT fallout from commit 4bcc595ccd80
> ("printk: reinstate KERN_CONT for printing continuation lines"), but
> the code still has unnecessary KERN_CONT uses.
>
> Remove the KERN_CONT uses to avoid possible message interleaving.
>
> Miscellanea:
>
> o Remove unnecessary trailing blank from the output too.
> o Convert i and top_reg to unsigned int
> o Move the extra blank line after __show_reg to the caller for symmetry
> Signed-off-by: Joe Perches <joe@perches.com>
> ---
> arch/arm64/kernel/process.c | 21 ++++++++++-----------
> 1 file changed, 10 insertions(+), 11 deletions(-)
>
> diff --git a/arch/arm64/kernel/process.c b/arch/arm64/kernel/process.c
> index 01753cd7d3f0..5ba12f019bf7 100644
> --- a/arch/arm64/kernel/process.c
> +++ b/arch/arm64/kernel/process.c
> @@ -168,7 +168,7 @@ void machine_restart(char *cmd)
>
> void __show_regs(struct pt_regs *regs)
> {
> - int i, top_reg;
> + unsigned int i, top_reg;
This change is not necessary. These will work perfectly fine as ints;
please leave them as-is.
> u64 lr, sp;
>
> if (compat_user_mode(regs)) {
> @@ -190,24 +190,23 @@ void __show_regs(struct pt_regs *regs)
>
> i = top_reg;
>
> - while (i >= 0) {
> - printk("x%-2d: %016llx ", i, regs->regs[i]);
> + if (i % 2) {
This should be:
if (i % 2 == 0) {
Otherwise we'll lose x0 in the native case (and x29 will be given a line
of its own).
> + printk("x%-2d: %016llx\n", i, regs->regs[i]);
> i--;
> -
> - if (i % 2 == 0) {
> - pr_cont("x%-2d: %016llx ", i, regs->regs[i]);
> - i--;
> - }
> -
> - pr_cont("\n");
> }
> - printk("\n");
> + while (i > 0) {
> + printk("x%-2d: %016llx x%-2d: %016llx\n",
> + i, regs->regs[i],
> + i - 1, regs->regs[i - 1]);
> + i -= 2;
> + }
> }
>
> void show_regs(struct pt_regs * regs)
> {
> printk("\n");
> __show_regs(regs);
> + printk("\n");
> }
Other functions call __show_regs() directly and the trailing newline
there is expected. Please leave it in __show_regs().
Otherwise, this looks fine to me.
Thanks,
Mark.
^ permalink raw reply
* [PATCH 2/3] ARM: convert to generated system call tables
From: Geert Uytterhoeven @ 2016-10-25 17:09 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <4146248.jXuviLlvH5@wuerfel>
On Tue, Oct 25, 2016 at 12:28 PM, Arnd Bergmann <arnd@arndb.de> wrote:
> On Tuesday, October 25, 2016 10:12:10 PM CEST Michael Cree wrote:
>> On Fri, Oct 21, 2016 at 03:06:45PM +0200, Arnd Bergmann wrote:
>> > I see your point, but I think there are serious issues with the current
>> > approach as well:
>> >
>> > - a lot of the less common architectures just don't get updated
>> > in time, out of 22 architectures that don't use asm-generic/unistd.h,
>> > only 12 have pwritev2 in linux-next, and only three have pkey_mprotect
>> >
>> > - some architectures that add all syscalls sometimes make a mistake
>> > and forget one, e.g. alpha apparently never added __NR_bpf, but it
>> > did add the later __NR_execveat.
>>
>> __NR_bpf was not forgotten on Alpha. It was not wired up because
>> extra architecture support is needed which has not been implemented.
>>
>> But maybe we should just wire it up to sys_ni_syscall in the meantime
>> so a syscall number is reserved for it, and user space can call it to
>> get -ENOSYS returned.
>
> Ah, I must have misinterpreted the code then. I assumed that the
> bpf syscall always works on all architectures, but that only the
> jit compiler for it required architecture specific code to make it
> more efficient.
>
> The implementation of sys_bfp is compile-time selectable at the moment
> and falls back to sys_no_syscall if CONFIG_BPF_SYSCALL is disabled.
> If it doesn't work on Alpha, maybe that symbol could have a "depends
> on !ALPHA" or "depends on BPF_SUPPORT"?
Yes, BPF should just work (m68k has it).
> sys_seccomp is another one that falls into a similar category, but
> it already depends on HAVE_ARCH_SECCOMP_FILTER, and most other
> architectures have assigned a syscall number but not set this symbol.
> This one will actually allow you to set strict seccomp mode even
> without the Kconfig symbol, just not allow to set a filter.
Seccomp needs architecture support (m68k doesn't have it).
Gr{oetje,eeting}s,
Geert
--
Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- geert at linux-m68k.org
In personal conversations with technical people, I call myself a hacker. But
when I'm talking to journalists I just say "programmer" or something like that.
-- Linus Torvalds
^ permalink raw reply
* [PATCH] tty/serial: at91: fix hardware handshake on Atmel platforms
From: Uwe Kleine-König @ 2016-10-25 17:17 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161025161135.7316-1-richard.genoud@gmail.com>
Hello,
On Tue, Oct 25, 2016 at 06:11:35PM +0200, Richard Genoud wrote:
> commit 1cf6e8fc8341 ("tty/serial: at91: fix RTS line management when
> hardware handshake is enabled"), despite its title, broke hardware
> handshake on *every* Atmel platforms.
s/platforms/platform/
> The only one partially working is the SAMA5D2.
>
> To understand why, one has to understand the flag ATMEL_US_USMODE_HWHS
> first:
> Before commit 1cf6e8fc8341 ("tty/serial: at91: fix RTS line management
> when hardware handshake is enabled"), this flag was never set.
> Thus, the CTS/RTS where only handled by serial_core (and everything
> worked just fine).
>
> This commit introduced the use of the ATMEL_US_USMODE_HWHS flag,
> enabling it for all boards when the user space enables flow control.
>
> When the ATMEL_US_USMODE_HWHS is set, the Atmel USART controller
> handles a part of the flow control job:
> - disable the transmitter when the CTS pin gets high.
> - drive the RTS pin high when the DMA buffer transfer is completed or
> PDC RX buffer full or RX FIFO is beyond threshold. (depending on the
> controller version).
I don't understand the DMA buffer part.
> NB: This feature is *not* mandatory for the flow control to work.
>
> Now, the specifics of the ATMEL_US_USMODE_HWHS flag:
>
> - For platforms with DMAC and no FIFOs (sam9x25, sam9x35, sama5D3,
> sama5D4, sam9g15, sam9g25, sam9g35)* this feature simply doesn't work.
> ( source: https://lkml.org/lkml/2016/9/7/598 )
What does "doesn't work" mean? Is ATMEL_US_USMODE_HWHS a noop, or does
it break something?
> Tested it on sam9g35, the RTS pins always stays up, even when RXEN=1
> or a new DMA transfer descriptor is set.
> => ATMEL_US_USMODE_HWHS should not be used for those platforms
Depending on the answer to the above question it might not matter if it
is set or not.
> - For platforms with a PDC (sam926{0,1,3}, sam9g10, sam9g20, sam9g45,
> sam9g46)*, there's another kind of problem. Once the flag
> ATMEL_US_USMODE_HWHS is set, the RTS pin can't be driven anymore via
> RTSEN/RTSDIS in USART Control Register. The RTS pin can only be driven
> by enabling/disabling the receiver or setting RCR=RNCR=0 in the PDC
> (Receive (Next) Counter Register).
> => Doing this is beyond the scope of this patch and could add other
> bugs, so the original (and working) behaviour should be set for those
> platforms (meaning ATMEL_US_USMODE_HWHS flag should be unset).
Then maybe just revert the faulty patch for now and do it better later
on top of this?
> - For platforms with a FIFO (sama5d2)*, the RTS pin is driven according
> to the RX FIFO thresholds, and can be also driven by RTSEN/RTSDIS in
> USART Control Register. No problem here.
> (This was the use case of commit 1cf6e8fc8341 ("tty/serial: at91: fix
> RTS line management when hardware handshake is enabled"))
> NB: If the CTS pin declared as a GPIO in the DTS, (for instance
> cts-gpios = <&pioA PIN_PB31 GPIO_ACTIVE_LOW>), the transmitter will be
> disabled.
> => ATMEL_US_USMODE_HWHS flag can be set for this platform ONLY IF the
> CTS pin is not a GPIO.
How did you test this? What I consider interesting here is if the
hardware CTS function was muxed on a pin and in which state this pin (if
any) is. If it is not muxed anywhere and disables the transmitter
because of an internal pull up that is IMHO a hw bug and should be
mentioned more explicitly in the comment.
> So, the only case when ATMEL_US_USMODE_HWHS can be enabled is when
> (atmel_use_fifo(port) &&
> !mctrl_gpio_to_gpiod(atmel_port->gpios, UART_GPIO_CTS))
>
> Tested on all Atmel USART controller flavours:
> AT91SAM9G35-CM, AT91SAM9G20-EK and SAMA5D2xplained
> ^^^^ ^^^^ ^^^^
> (DMAC flavour), (PDC flavour) and (FIFO flavour)
I'd write that as: Tested on all Atmel USART controller flavours:
AT91SAM9G35-CM (DMAC flavour), AT91SAM9G20-EK (PDC flavour),
SAMA5D2xplained (FIFO flavour).
> Changes since v4:
> - the mctrl_gpio_use_rtscts() is gone since it was atmel_serial
> specific. (so patch 1 is gone)
> - patches 2 and 3 have been merged together since it didn't make
> a lot of sense to correct the GPIO case in one separate patch.
> - ATMEL_US_USMODE_HWHS is now unset for platform with PDC
>
> Changes since v3:
> - remove superfluous #include <linux/err.h> (thanks to Uwe)
> - rebase on next-20160930
>
> Changes since v2:
> - remove IS_ERR_OR_NULL() test in patch 1/3 as Uwe suggested.
> - fix typos in patch 2/3
> - rebase on next-20160927
> - simplify the logic in patch 3/3.
>
> Changes since v1:
> - Correct patch 1 with the error found by kbuild.
> - Add Alexandre's Acked-by on patch 2
> - Rewrite patch 3 logic in the light of the on-going discussion
> with Cyrille and Alexandre.
>
> * the list may not be exhaustive
Add a Fixes: line please.
> Signed-off-by: Richard Genoud <richard.genoud@gmail.com>
> ---
> drivers/tty/serial/atmel_serial.c | 25 +++++++++++++++++++++----
> 1 file changed, 21 insertions(+), 4 deletions(-)
>
> I think this should go in the stable tree since it fixes the flow
> control broken since v4.0.
> But It won't compile on versions before 4.9rc1 because:
> function atmel_use_fifo was introduced in 4.4.12 / 4.7
> variable atmel_port was introduced in 4.9rc1
>
> That's why I didn't add the Cc stable in the email body.
>
>
> diff --git a/drivers/tty/serial/atmel_serial.c b/drivers/tty/serial/atmel_serial.c
> index fd8aa1f4ba78..2c7c45904ba7 100644
> --- a/drivers/tty/serial/atmel_serial.c
> +++ b/drivers/tty/serial/atmel_serial.c
> @@ -2132,11 +2132,28 @@ static void atmel_set_termios(struct uart_port *port, struct ktermios *termios,
> mode |= ATMEL_US_USMODE_RS485;
> } else if (termios->c_cflag & CRTSCTS) {
> /* RS232 with hardware handshake (RTS/CTS) */
> - if (atmel_use_dma_rx(port) && !atmel_use_fifo(port)) {
> - dev_info(port->dev, "not enabling hardware flow control because DMA is used");
> - termios->c_cflag &= ~CRTSCTS;
This if was not introduced in commit 1cf6e8fc8341. Is it still right to
remove this here?
> - } else {
> + if (atmel_use_fifo(port) &&
> + !mctrl_gpio_to_gpiod(atmel_port->gpios, UART_GPIO_CTS)) {
> + /*
> + * with ATMEL_US_USMODE_HWHS set, the controller will
> + * be able to drive the RTS pin high/low when the RX
> + * FIFO is above RXFTHRES/below RXFTHRES2.
> + * It will also disable the transmitter when the CTS
> + * pin is high.
> + * This mode is not activated if CTS pin is a GPIO
> + * because in this case, the transmitter is always
> + * disabled.
> + * If the RTS pin is a GPIO, the controller won't be
> + * able to drive it according to the FIFO thresholds,
> + * but it will be handled by the driver.
> + */
> mode |= ATMEL_US_USMODE_HWHS;
> + } else {
> + /*
> + * For platforms without FIFO, the flow control is
> + * handled by the driver.
> + */
> + mode |= ATMEL_US_USMODE_NORMAL;
> }
> } else {
> /* RS232 without hadware handshake */
(unrelated to this patch) s/hadware/hardware/
--
Pengutronix e.K. | Uwe Kleine-K?nig |
Industrial Linux Solutions | http://www.pengutronix.de/ |
^ permalink raw reply
* [PATCH V2] arm64: Neaten show_regs, remove KERN_CONT
From: Joe Perches @ 2016-10-25 17:29 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161025170745.GE8898@leverpostej>
On Tue, 2016-10-25 at 18:07 +0100, Mark Rutland wrote:
> On Tue, Oct 25, 2016 at 09:40:26AM -0700, Joe Perches wrote:
> > commit db4b0710fae9 ("arm64: fix show_regs fallout from KERN_CONT changes")
> > corrected the KERN_CONT fallout from commit 4bcc595ccd80
> > ("printk: reinstate KERN_CONT for printing continuation lines"), but
> > the code still has unnecessary KERN_CONT uses.
> >
> > Remove the KERN_CONT uses to avoid possible message interleaving.
Hey Mark.
Please fix it as you think appropriate.
No credit to me is necessary.
cheers, Joe
^ permalink raw reply
* [PATCH/RFT v2 12/17] USB: ochi-da8xx: Use a regulator for vbus/overcurrent
From: Axel Haslam @ 2016-10-25 17:32 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <09a4391e-63b6-1622-f964-4aff0ecae87c@lechnology.com>
On Tue, Oct 25, 2016 at 6:53 PM, David Lechner <david@lechnology.com> wrote:
> On 10/25/2016 03:24 AM, Axel Haslam wrote:
>>
>> On Tue, Oct 25, 2016 at 3:39 AM, David Lechner <david@lechnology.com>
>> wrote:
>>>
>>> On 10/24/2016 11:46 AM, ahaslam at baylibre.com wrote:
>>>>
>>>>
>>>> From: Axel Haslam <ahaslam@baylibre.com>
>>>>
>>>> Currently, the da8xx ohci driver uses a set of gpios and callbacks in
>>>> board files to handle vbus and overcurrent irqs form the power supply.
>>>> However, this does not play nice when moving to a DT based boot were
>>>> we wont have board files.
>>>>
>>>> Instead of requesting and handling the gpio, use the regulator framework
>>>> to take care of enabling and disabling vbus power.
>>>> This has the benefit
>>>> that we dont need to pass any more platform data to the driver:
>>>>
>>>> These will be handled by the regulator framework:
>>>> set_power -> regulator_enable/regulator_disable
>>>> get_power -> regulator_is_enabled
>>>> get_oci -> regulator_get_mode
>>>> ocic_notify -> regulator notification
>>>>
>>>> We can keep the default potpgt and use the regulator start delay
>>>> instead:
>>>> potpgt -> regulator startup delay time
>>>>
>>>> The hawk board does not have a GPIO/OVERCURRENT gpio to control vbus,
>>>> (they should not have been decleared/reserved) so, just remove those
>>>> definitions from the hwk board file.
>>>>
>>>> Signed-off-by: Axel Haslam <ahaslam@baylibre.com>
>>>> ---
>>>
>>>
>>>
>>>
>>> How do you recover after an overcurrent event?
>>>
>>> I have configured a fixed-regulator using device-tree, but similar to the
>>> configuration in the board files here. However, when I shorted out the
>>> VBUS
>>> and caused an overcurrent event, I see nothing in the kernel log saying
>>> that
>>> there was an overcurrent event and after I remove the short, the
>>> regulator
>>> is never turned back on.
>>>
>>>
>>
>> You should have the patch to fix gpiolib, and you should declare the
>> over current gpio on the regulator as such:
>> (if the pin is enabled high you should add oc-active-high);
>>
>> vbus_fixed: fixed-regulator-vbus {
>> compatible = "regulator-fixed";
>> gpio = <&gpio 109 0>;
>> oc-gpio = <&gpio 36 0>;
>> regulator-boot-on;
>> enable-active-high;
>> regulator-name = "vbus";
>> regulator-min-microvolt = <5000000>;
>> regulator-max-microvolt = <5000000>;
>> };
>>
>>
>> Question: Do you see that the over current gpio was requested
>> in debugfs/gpio? and, do you see the interrupt in /proc/interrupts?
>>
>> If you unplug and plug in back the usb device it should work again.
>> also you can unbind and bind it should also start to work:
>> something like:
>>
>> echo usb1 >/sys/bus/usb/drivers/usb/unbind
>> echo usb1 >/sys/bus/usb/drivers/usb/bind
>>
>>
>
> I have added oc-active-high and I get different results, but it is still not
> quite right. When I short the VBUS, I can see that my overcurrent gpio
> changes state. However, the driver does not turn of the VBUS. When I remove
> the short, I get an overcurrent error in the kernel log. I would expect this
> when I create the short, not when I remove it. I also tried adding
> GPIO_ACTIVE_LOW to the oc-gpio, but this did not change the behavior. In
> either case, the oc_gpio shows as high under normal conditions, so perhaps
> there is a problem with the gpio-davinci driver not picking up
> GPIO_ACTIVE_LOW from the device tree.
>
>
> My regulator is basically the same. My device just uses different gpios.
>
> vbus_reg: vbus-reg {
> compatible = "regulator-fixed";
> pinctrl-names = "default";
> pinctrl-0 = <&usb11_pins>;
> gpio = <&gpio 101 GPIO_ACTIVE_LOW>;
> oc-gpio = <&gpio 99 0>;
> enable-active-high;
> oc-active-high;
> regulator-name = "vbus";
> regulator-min-microvolt = <5000000>;
> regulator-max-microvolt = <5000000>;
> }
>
>
> It seems to me though that I should not have oc-active-high since under
> normal conditions, the oc_gpio is high and during an overcurrent event, the
in my board the over current gpio is active low too, i was just mentiontioning
to add that in case yours was not.
> oc_gpio is low. Double-checking the behavior without oc-active-high, I see
> that the vbus gpio is turned off in response to the overcurrent event, but I
> don't get the overcurrent message in the kernel log. Perhaps this is because
> as soon as there is an overcurrent event the vbus turns off and the oc_gpio
> returns to normal before the usb driver has a chance to poll the overcurrent
> state?
Perhaps. i dont have a board that has overcurrent, or that i can
switch vbus off.
what is exactly the log you are refering to?
im wondering, was the behavior different before the patches?
it should be the same without the patches.
>
> Also, unplugging the device and plugging it back in does nothing. Unbinding
> and binding the driver does work, but that does not seem like a very nice
> way to have to recover from an overcurrent event.
im guessing that unplug and plug wont work as vbus is gone and
we cannot detect it anymore (contrary to my setup were i always have vbus)
sorry for suggesting that before.
we could recover vbus automatically form the notification,
(when the over-current condition disappears) but then im afraid we
might oscillate, even if we retry after some timeout. so perhaps
bind/unbind is the right thing to do, as it requires the user to correct
the problem. I dont know if there is a better solution.
>
>
>
^ permalink raw reply
* [PATCH] ARM: imx6: Fix GPC probe error path
From: Guenter Roeck @ 2016-10-25 17:34 UTC (permalink / raw)
To: linux-arm-kernel
GPC may fail to instantiate with
imx-gpc: probe of 20dc000.gpc failed with error -22
which is returned from of_genpd_add_provider_onecell(). The error path
does not call pm_genpd_remove(). This results in the following crash
later on.
Unhandled fault: page domain fault (0x01b) at 0x00000040
pgd = c0204000
[00000040] *pgd=00000000
Internal error: : 1b [#1] SMP ARM
Modules linked in:
CPU: 0 PID: 108 Comm: kworker/0:3 Not tainted 4.9.0-rc2 #8
Hardware name: Freescale i.MX6 Quad/DualLite (Device Tree)
Workqueue: pm genpd_power_off_work_fn
task: c759ea00 task.stack: c766a000
PC is at mutex_lock+0xc/0x4c
LR is at regulator_disable+0x28/0x64
...
[<c0bc2694>] (mutex_lock) from [<c06e4e8c>] (regulator_disable+0x28/0x64)
[<c06e4e8c>] (regulator_disable) from [<c0323b68>] (imx6q_pm_pu_power_off+0x90/0x98)
[<c0323b68>] (imx6q_pm_pu_power_off) from [<c07efb04>] (genpd_poweroff+0x114/0x1d4)
[<c07efb04>] (genpd_poweroff) from [<c07efdc0>] (genpd_power_off_work_fn+0x20/0x2c)
[<c07efdc0>] (genpd_power_off_work_fn) from [<c0358f70>] (process_one_work+0x138/0x34c)
[<c0358f70>] (process_one_work) from [<c03591bc>] (worker_thread+0x38/0x510)
[<c03591bc>] (worker_thread) from [<c035e48c>] (kthread+0xdc/0xf4)
[<c035e48c>] (kthread) from [<c0307eb8>] (ret_from_fork+0x14/0x3c)
This is seen with multi_v7_defconfig and imx6dl-sabrelite.dtb running in
qemu (v2.7 patched to fix a qemu related problem). The error return from
of_genpd_add_provider_onecell() is not seen in v4.8 and may be caused by
a devicetree change (this is a wild guess only), but that is a different
problem.
Fixes: 00eb60a8b4f7 ("ARM: imx6: gpc: Add PU power domain for GPU/VPU")
Cc: Philipp Zabel <p.zabel@pengutronix.de>
Cc: Arnd Bergmann <arnd@arndb.de>
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
---
Several bisect attempts trying to track down "imx-gpc: probe ... failed
with error -22" point to commit 00e729c93395 ("Merge tag 'armsoc-dt' of
git://git.kernel.org/pub/scm/linux/kernel/git/arm/arm-soc"). I have not
been able to track down the real culprit. Part of the problem is that
CONFIG_REGULATOR_ANATOP must be enabled for the problem to be seen, and
CONFIG_ARCH_AT91 causes compile errors for some sequence of commits between
v4.8 and v4.9-rc1. But even after taking this into account, the bisect
results always point to 00e729c93395. If anyone has an idea how to track
down that problem, or what might be causing it, please let me know.
arch/arm/mach-imx/gpc.c | 10 ++++++++--
1 file changed, 8 insertions(+), 2 deletions(-)
diff --git a/arch/arm/mach-imx/gpc.c b/arch/arm/mach-imx/gpc.c
index 0df062d8b2c9..f3f40045b4c9 100644
--- a/arch/arm/mach-imx/gpc.c
+++ b/arch/arm/mach-imx/gpc.c
@@ -409,6 +409,7 @@ static int imx_gpc_genpd_init(struct device *dev, struct regulator *pu_reg)
{
struct clk *clk;
int i;
+ int ret;
imx6q_pu_domain.reg = pu_reg;
@@ -431,9 +432,14 @@ static int imx_gpc_genpd_init(struct device *dev, struct regulator *pu_reg)
return 0;
pm_genpd_init(&imx6q_pu_domain.base, NULL, false);
- return of_genpd_add_provider_onecell(dev->of_node,
- &imx_gpc_onecell_data);
+ ret = of_genpd_add_provider_onecell(dev->of_node,
+ &imx_gpc_onecell_data);
+ if (ret)
+ goto genpd_remove;
+ return 0;
+genpd_remove:
+ pm_genpd_remove(&imx6q_pu_domain.base);
clk_err:
while (i--)
clk_put(imx6q_pu_domain.clk[i]);
--
2.5.0
^ permalink raw reply related
* [PATCH V4 0/5] firmware: Add support for TI System Control Interface (TI-SCI) protocol driver
From: Tero Kristo @ 2016-10-25 17:34 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161018230837.6515-1-nm@ti.com>
On 19/10/16 02:08, Nishanth Menon wrote:
> Version 4 of the series is basically a rebase to v4.9-rc1, no functional
> changes.
Hi,
Any final comments on this series, or shall I send a pull-req forward?
Very minimal changes compared to v3 so should be good to go imo.
-Tero
>
> Texas Instruments' Keystone generation System on Chips (SoC)
> starting with 66AK2G02[1], now include a dedicated SoC System Control
> entity called PMMC(Power Management Micro Controller) in line with
> ARM architecture recommendations. The function of this module is
> to integrate all system operations in a centralized location.
> Communication with the SoC System Control entity from various
> processing units like ARM/DSP occurs over Message Manager hardware
> block.
>
> This series adds the base support for TI System Control Interface
> (TI-SCI) protocol[2]. The protocol is built on top of Texas
> Instrument's Message Manager communication mechanism[3].
>
> Overall architecture is very similar to SCPI[4] as follows:
> +-------------+ +---------+ +------^-----+
> | TI SCI GENPD| |TISCI Clk| |TISCI reset |
> +------+------+ +----+----+ +------+-----+
> | | |
> | +----v--------------+ |
> +----------> TISCI Protocol(*) <--+
> +----+--------------+
> |
> +---v-----------+
> | MAILBOX FWK |
> +---+-----------+
> |
> +---v-----------+
> | TI MSGMGR |-> TISCI hardware block
> +---------------+
> (*) This series.
>
>
> V4 of the series is based off v4.9-rc1 and is also available here:
> https://github.com/nmenon/linux-2.6-playground/commits/upstream/v4.10/tisci-base-v4
> Quick boot test: http://pastebin.ubuntu.com/23346183/
>
> Changes since v3:
> - rebase to v4.9-rc1
> - minor checkpatch fixes
>
> V3: https://lkml.org/lkml/2016/9/6/747
> V2: https://lkml.org/lkml/2016/8/30/273
> V1: https://lkml.org/lkml/2016/8/19/768
>
> Nishanth Menon (5):
> Documentation: Add support for TI System Control Interface (TI-SCI)
> protocol
> firmware: Add basic support for TI System Control Interface (TI-SCI)
> protocol
> firmware: ti_sci: Add support for Device control
> firmware: ti_sci: Add support for Clock control
> firmware: ti_sci: Add support for reboot core service
>
> .../devicetree/bindings/arm/keystone/ti,sci.txt | 81 +
> MAINTAINERS | 10 +
> drivers/firmware/Kconfig | 15 +
> drivers/firmware/Makefile | 1 +
> drivers/firmware/ti_sci.c | 1991 ++++++++++++++++++++
> drivers/firmware/ti_sci.h | 492 +++++
> include/linux/soc/ti/ti_sci_protocol.h | 249 +++
> 7 files changed, 2839 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/arm/keystone/ti,sci.txt
> create mode 100644 drivers/firmware/ti_sci.c
> create mode 100644 drivers/firmware/ti_sci.h
> create mode 100644 include/linux/soc/ti/ti_sci_protocol.h
>
^ permalink raw reply
* [PATCH 3/4] usb: musb: da8xx: Add DT support for the DA8xx driver
From: Sergei Shtylyov @ 2016-10-25 17:38 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1477406345-27192-4-git-send-email-abailon@baylibre.com>
Hello.
On 10/25/2016 05:39 PM, Alexandre Bailon wrote:
> From: Petr Kulhavy <petr@barix.com>
>
> This adds DT support for TI DA8xx/OMAP-L1x/AM17xx/AM18xx MUSB driver
>
> Signed-off-by: Petr Kulhavy <petr@barix.com>
> Signed-off-by: Alexandre Bailon <abailon@baylibre.com>
> ---
> drivers/usb/musb/da8xx.c | 76 ++++++++++++++++++++++++++++++++++++++++++------
> 1 file changed, 67 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/usb/musb/da8xx.c b/drivers/usb/musb/da8xx.c
> index 210b7e4..d465087 100644
> --- a/drivers/usb/musb/da8xx.c
> +++ b/drivers/usb/musb/da8xx.c
> @@ -6,6 +6,9 @@
> * Based on the DaVinci "glue layer" code.
> * Copyright (C) 2005-2006 by Texas Instruments
> *
> + * DT support
> + * Copyright (c) 2016 Petr Kulhavy <petr@barix.com>
> + *
> * This file is part of the Inventra Controller Driver for Linux.
> *
> * The Inventra Controller Driver for Linux is free software; you
[...]
> @@ -499,15 +537,21 @@ static int da8xx_probe(struct platform_device *pdev)
> memset(musb_resources, 0x00, sizeof(*musb_resources) *
> ARRAY_SIZE(musb_resources));
>
> - musb_resources[0].name = pdev->resource[0].name;
> - musb_resources[0].start = pdev->resource[0].start;
> - musb_resources[0].end = pdev->resource[0].end;
> - musb_resources[0].flags = pdev->resource[0].flags;
> + res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
> + if (!res) {
> + dev_err(&pdev->dev, "failed to get memory.\n");
> + ret = -EINVAL;
> + goto err_unregister_usb_phy;
> + }
> + musb_resources[0] = *res;
What does this change have to do with the DT conversion?
>
> - musb_resources[1].name = pdev->resource[1].name;
> - musb_resources[1].start = pdev->resource[1].start;
> - musb_resources[1].end = pdev->resource[1].end;
> - musb_resources[1].flags = pdev->resource[1].flags;
> + res = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
> + if (!res) {
> + dev_err(&pdev->dev, "failed to get irq.\n");
> + ret = -EINVAL;
> + goto err_unregister_usb_phy;
> + }
> + musb_resources[1] = *res;
And this?
I'm also concerned that you'd copy the resource linkage fields which the
existing code avoids...
[...]
MBR, Sergei
^ permalink raw reply
* [PATCH] arm64: Neaten show_regs, remove KERN_CONT
From: Linus Torvalds @ 2016-10-25 17:38 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161024164255.GN15620@leverpostej>
On Mon, Oct 24, 2016 at 9:42 AM, Mark Rutland <mark.rutland@arm.com> wrote:
>
> That does not appear to be the case; as fr as I can tell the core prints a
> timestamp per line as required. If I run:
>
> printk("TEST\nLINE1\nLINE2\nLINE3\nLINE4\n");
Please don't do this.
It has historically not worked well, and it still doesn't actually
work reliably. In particular, it currently works in the *logs* (ie
dmesg), but not necessarily on screen (because "msg_print_text()" does
do the "look for newlines in the middle", but console_cont_flush()
does not).
It so happens that the patch I've been sending people probably fixes
that odd case too, almost entirely by mistake (if "by mistake" you
mean "it gets rid of the insane special cases that cause problems like
this").
So you can try the attached patch. It likely fixes your issues simply
because it removes all the crazy code.
Linus
-------------- next part --------------
kernel/printk/printk.c | 255 +++++++++++--------------------------------------
1 file changed, 58 insertions(+), 197 deletions(-)
diff --git a/kernel/printk/printk.c b/kernel/printk/printk.c
index de08fc90baaf..e63aa679614e 100644
--- a/kernel/printk/printk.c
+++ b/kernel/printk/printk.c
@@ -367,7 +367,6 @@ DECLARE_WAIT_QUEUE_HEAD(log_wait);
/* the next printk record to read by syslog(READ) or /proc/kmsg */
static u64 syslog_seq;
static u32 syslog_idx;
-static enum log_flags syslog_prev;
static size_t syslog_partial;
/* index and sequence number of the first record stored in the buffer */
@@ -381,7 +380,6 @@ static u32 log_next_idx;
/* the next printk record to write to the console */
static u64 console_seq;
static u32 console_idx;
-static enum log_flags console_prev;
/* the next printk record to read after the last 'clear' command */
static u64 clear_seq;
@@ -650,27 +648,15 @@ static void append_char(char **pp, char *e, char c)
}
static ssize_t msg_print_ext_header(char *buf, size_t size,
- struct printk_log *msg, u64 seq,
- enum log_flags prev_flags)
+ struct printk_log *msg, u64 seq)
{
u64 ts_usec = msg->ts_nsec;
- char cont = '-';
do_div(ts_usec, 1000);
- /*
- * If we couldn't merge continuation line fragments during the print,
- * export the stored flags to allow an optional external merge of the
- * records. Merging the records isn't always neccessarily correct, like
- * when we hit a race during printing. In most cases though, it produces
- * better readable output. 'c' in the record flags mark the first
- * fragment of a line, '+' the following.
- */
- if (msg->flags & LOG_CONT)
- cont = (prev_flags & LOG_CONT) ? '+' : 'c';
-
return scnprintf(buf, size, "%u,%llu,%llu,%c;",
- (msg->facility << 3) | msg->level, seq, ts_usec, cont);
+ (msg->facility << 3) | msg->level, seq, ts_usec,
+ msg->flags & LOG_CONT ? 'c' : '-');
}
static ssize_t msg_print_ext_body(char *buf, size_t size,
@@ -725,7 +711,6 @@ static ssize_t msg_print_ext_body(char *buf, size_t size,
struct devkmsg_user {
u64 seq;
u32 idx;
- enum log_flags prev;
struct ratelimit_state rs;
struct mutex lock;
char buf[CONSOLE_EXT_LOG_MAX];
@@ -794,7 +779,7 @@ static ssize_t devkmsg_write(struct kiocb *iocb, struct iov_iter *from)
return ret;
}
-static void cont_flush(void);
+static void deferred_cont_flush(void);
static ssize_t devkmsg_read(struct file *file, char __user *buf,
size_t count, loff_t *ppos)
@@ -811,7 +796,6 @@ static ssize_t devkmsg_read(struct file *file, char __user *buf,
if (ret)
return ret;
raw_spin_lock_irq(&logbuf_lock);
- cont_flush();
while (user->seq == log_next_seq) {
if (file->f_flags & O_NONBLOCK) {
ret = -EAGAIN;
@@ -838,12 +822,11 @@ static ssize_t devkmsg_read(struct file *file, char __user *buf,
msg = log_from_idx(user->idx);
len = msg_print_ext_header(user->buf, sizeof(user->buf),
- msg, user->seq, user->prev);
+ msg, user->seq);
len += msg_print_ext_body(user->buf + len, sizeof(user->buf) - len,
log_dict(msg), msg->dict_len,
log_text(msg), msg->text_len);
- user->prev = msg->flags;
user->idx = log_next(user->idx);
user->seq++;
raw_spin_unlock_irq(&logbuf_lock);
@@ -860,6 +843,7 @@ static ssize_t devkmsg_read(struct file *file, char __user *buf,
ret = len;
out:
mutex_unlock(&user->lock);
+ deferred_cont_flush();
return ret;
}
@@ -874,7 +858,6 @@ static loff_t devkmsg_llseek(struct file *file, loff_t offset, int whence)
return -ESPIPE;
raw_spin_lock_irq(&logbuf_lock);
- cont_flush();
switch (whence) {
case SEEK_SET:
/* the first record */
@@ -913,7 +896,6 @@ static unsigned int devkmsg_poll(struct file *file, poll_table *wait)
poll_wait(file, &log_wait, wait);
raw_spin_lock_irq(&logbuf_lock);
- cont_flush();
if (user->seq < log_next_seq) {
/* return error when data has vanished underneath us */
if (user->seq < log_first_seq)
@@ -922,6 +904,7 @@ static unsigned int devkmsg_poll(struct file *file, poll_table *wait)
ret = POLLIN|POLLRDNORM;
}
raw_spin_unlock_irq(&logbuf_lock);
+ deferred_cont_flush();
return ret;
}
@@ -1226,26 +1209,12 @@ static size_t print_prefix(const struct printk_log *msg, bool syslog, char *buf)
return len;
}
-static size_t msg_print_text(const struct printk_log *msg, enum log_flags prev,
- bool syslog, char *buf, size_t size)
+static size_t msg_print_text(const struct printk_log *msg, bool syslog, char *buf, size_t size)
{
const char *text = log_text(msg);
size_t text_size = msg->text_len;
- bool prefix = true;
- bool newline = true;
size_t len = 0;
- if ((prev & LOG_CONT) && !(msg->flags & LOG_PREFIX))
- prefix = false;
-
- if (msg->flags & LOG_CONT) {
- if ((prev & LOG_CONT) && !(prev & LOG_NEWLINE))
- prefix = false;
-
- if (!(msg->flags & LOG_NEWLINE))
- newline = false;
- }
-
do {
const char *next = memchr(text, '\n', text_size);
size_t text_len;
@@ -1263,22 +1232,17 @@ static size_t msg_print_text(const struct printk_log *msg, enum log_flags prev,
text_len + 1 >= size - len)
break;
- if (prefix)
- len += print_prefix(msg, syslog, buf + len);
+ len += print_prefix(msg, syslog, buf + len);
memcpy(buf + len, text, text_len);
len += text_len;
- if (next || newline)
- buf[len++] = '\n';
+ buf[len++] = '\n';
} else {
/* SYSLOG_ACTION_* buffer size only calculation */
- if (prefix)
- len += print_prefix(msg, syslog, NULL);
+ len += print_prefix(msg, syslog, NULL);
len += text_len;
- if (next || newline)
- len++;
+ len++;
}
- prefix = true;
text = next;
} while (text);
@@ -1300,12 +1264,10 @@ static int syslog_print(char __user *buf, int size)
size_t skip;
raw_spin_lock_irq(&logbuf_lock);
- cont_flush();
if (syslog_seq < log_first_seq) {
/* messages are gone, move to first one */
syslog_seq = log_first_seq;
syslog_idx = log_first_idx;
- syslog_prev = 0;
syslog_partial = 0;
}
if (syslog_seq == log_next_seq) {
@@ -1315,13 +1277,11 @@ static int syslog_print(char __user *buf, int size)
skip = syslog_partial;
msg = log_from_idx(syslog_idx);
- n = msg_print_text(msg, syslog_prev, true, text,
- LOG_LINE_MAX + PREFIX_MAX);
+ n = msg_print_text(msg, true, text, LOG_LINE_MAX + PREFIX_MAX);
if (n - syslog_partial <= size) {
/* message fits into buffer, move forward */
syslog_idx = log_next(syslog_idx);
syslog_seq++;
- syslog_prev = msg->flags;
n -= syslog_partial;
syslog_partial = 0;
} else if (!len){
@@ -1360,12 +1320,10 @@ static int syslog_print_all(char __user *buf, int size, bool clear)
return -ENOMEM;
raw_spin_lock_irq(&logbuf_lock);
- cont_flush();
if (buf) {
u64 next_seq;
u64 seq;
u32 idx;
- enum log_flags prev;
/*
* Find first record that fits, including all following records,
@@ -1373,12 +1331,10 @@ static int syslog_print_all(char __user *buf, int size, bool clear)
*/
seq = clear_seq;
idx = clear_idx;
- prev = 0;
while (seq < log_next_seq) {
struct printk_log *msg = log_from_idx(idx);
- len += msg_print_text(msg, prev, true, NULL, 0);
- prev = msg->flags;
+ len += msg_print_text(msg, true, NULL, 0);
idx = log_next(idx);
seq++;
}
@@ -1386,12 +1342,10 @@ static int syslog_print_all(char __user *buf, int size, bool clear)
/* move first record forward until length fits into the buffer */
seq = clear_seq;
idx = clear_idx;
- prev = 0;
while (len > size && seq < log_next_seq) {
struct printk_log *msg = log_from_idx(idx);
- len -= msg_print_text(msg, prev, true, NULL, 0);
- prev = msg->flags;
+ len -= msg_print_text(msg, true, NULL, 0);
idx = log_next(idx);
seq++;
}
@@ -1404,7 +1358,7 @@ static int syslog_print_all(char __user *buf, int size, bool clear)
struct printk_log *msg = log_from_idx(idx);
int textlen;
- textlen = msg_print_text(msg, prev, true, text,
+ textlen = msg_print_text(msg, true, text,
LOG_LINE_MAX + PREFIX_MAX);
if (textlen < 0) {
len = textlen;
@@ -1412,7 +1366,6 @@ static int syslog_print_all(char __user *buf, int size, bool clear)
}
idx = log_next(idx);
seq++;
- prev = msg->flags;
raw_spin_unlock_irq(&logbuf_lock);
if (copy_to_user(buf + len, text, textlen))
@@ -1425,7 +1378,6 @@ static int syslog_print_all(char __user *buf, int size, bool clear)
/* messages are gone, move to next one */
seq = log_first_seq;
idx = log_first_idx;
- prev = 0;
}
}
}
@@ -1522,12 +1474,10 @@ int do_syslog(int type, char __user *buf, int len, int source)
/* Number of chars in the log buffer */
case SYSLOG_ACTION_SIZE_UNREAD:
raw_spin_lock_irq(&logbuf_lock);
- cont_flush();
if (syslog_seq < log_first_seq) {
/* messages are gone, move to first one */
syslog_seq = log_first_seq;
syslog_idx = log_first_idx;
- syslog_prev = 0;
syslog_partial = 0;
}
if (source == SYSLOG_FROM_PROC) {
@@ -1540,16 +1490,14 @@ int do_syslog(int type, char __user *buf, int len, int source)
} else {
u64 seq = syslog_seq;
u32 idx = syslog_idx;
- enum log_flags prev = syslog_prev;
error = 0;
while (seq < log_next_seq) {
struct printk_log *msg = log_from_idx(idx);
- error += msg_print_text(msg, prev, true, NULL, 0);
+ error += msg_print_text(msg, true, NULL, 0);
idx = log_next(idx);
seq++;
- prev = msg->flags;
}
error -= syslog_partial;
}
@@ -1563,6 +1511,7 @@ int do_syslog(int type, char __user *buf, int len, int source)
error = -EINVAL;
break;
}
+ deferred_cont_flush();
out:
return error;
}
@@ -1650,46 +1599,47 @@ static inline void printk_delay(void)
static struct cont {
char buf[LOG_LINE_MAX];
size_t len; /* length == 0 means unused buffer */
- size_t cons; /* bytes written to console */
struct task_struct *owner; /* task of first print*/
u64 ts_nsec; /* time of first print */
u8 level; /* log level of first message */
u8 facility; /* log facility of first message */
enum log_flags flags; /* prefix, newline flags */
- bool flushed:1; /* buffer sealed and committed */
} cont;
-static void cont_flush(void)
+static bool cont_flush(void)
{
- if (cont.flushed)
- return;
- if (cont.len == 0)
+ if (!cont.len)
+ return false;
+
+ log_store(cont.facility, cont.level, cont.flags, cont.ts_nsec,
+ NULL, 0, cont.buf, cont.len);
+ cont.len = 0;
+ return true;
+}
+
+static void flush_timer(unsigned long data)
+{
+ unsigned long flags;
+ bool did_flush;
+
+ raw_spin_lock_irqsave(&logbuf_lock, flags);
+ did_flush = cont_flush();
+ raw_spin_unlock_irqrestore(&logbuf_lock, flags);
+ if (did_flush)
+ wake_up_klogd();
+}
+
+static void deferred_cont_flush(void)
+{
+ static DEFINE_TIMER(timer, flush_timer, 0, 0);
+
+ if (!cont.len)
return;
- if (cont.cons) {
- /*
- * If a fragment of this line was directly flushed to the
- * console; wait for the console to pick up the rest of the
- * line. LOG_NOCONS suppresses a duplicated output.
- */
- log_store(cont.facility, cont.level, cont.flags | LOG_NOCONS,
- cont.ts_nsec, NULL, 0, cont.buf, cont.len);
- cont.flushed = true;
- } else {
- /*
- * If no fragment of this line ever reached the console,
- * just submit it to the store and free the buffer.
- */
- log_store(cont.facility, cont.level, cont.flags, 0,
- NULL, 0, cont.buf, cont.len);
- cont.len = 0;
- }
+ mod_timer(&timer, jiffies + HZ/10);
}
static bool cont_add(int facility, int level, enum log_flags flags, const char *text, size_t len)
{
- if (cont.len && cont.flushed)
- return false;
-
/*
* If ext consoles are present, flush and skip in-kernel
* continuation. See nr_ext_console_drivers definition. Also, if
@@ -1706,8 +1656,6 @@ static bool cont_add(int facility, int level, enum log_flags flags, const char *
cont.owner = current;
cont.ts_nsec = local_clock();
cont.flags = flags;
- cont.cons = 0;
- cont.flushed = false;
}
memcpy(cont.buf + cont.len, text, len);
@@ -1726,34 +1674,6 @@ static bool cont_add(int facility, int level, enum log_flags flags, const char *
return true;
}
-static size_t cont_print_text(char *text, size_t size)
-{
- size_t textlen = 0;
- size_t len;
-
- if (cont.cons == 0 && (console_prev & LOG_NEWLINE)) {
- textlen += print_time(cont.ts_nsec, text);
- size -= textlen;
- }
-
- len = cont.len - cont.cons;
- if (len > 0) {
- if (len+1 > size)
- len = size-1;
- memcpy(text + textlen, cont.buf + cont.cons, len);
- textlen += len;
- cont.cons = cont.len;
- }
-
- if (cont.flushed) {
- if (cont.flags & LOG_NEWLINE)
- text[textlen++] = '\n';
- /* got everything, release buffer */
- cont.len = 0;
- }
- return textlen;
-}
-
static size_t log_output(int facility, int level, enum log_flags lflags, const char *dict, size_t dictlen, char *text, size_t text_len)
{
/*
@@ -1999,11 +1919,9 @@ static u64 syslog_seq;
static u32 syslog_idx;
static u64 console_seq;
static u32 console_idx;
-static enum log_flags syslog_prev;
static u64 log_first_seq;
static u32 log_first_idx;
static u64 log_next_seq;
-static enum log_flags console_prev;
static struct cont {
size_t len;
size_t cons;
@@ -2015,17 +1933,16 @@ static char *log_dict(const struct printk_log *msg) { return NULL; }
static struct printk_log *log_from_idx(u32 idx) { return NULL; }
static u32 log_next(u32 idx) { return 0; }
static ssize_t msg_print_ext_header(char *buf, size_t size,
- struct printk_log *msg, u64 seq,
- enum log_flags prev_flags) { return 0; }
+ struct printk_log *msg,
+ u64 seq) { return 0; }
static ssize_t msg_print_ext_body(char *buf, size_t size,
char *dict, size_t dict_len,
char *text, size_t text_len) { return 0; }
static void call_console_drivers(int level,
const char *ext_text, size_t ext_len,
const char *text, size_t len) {}
-static size_t msg_print_text(const struct printk_log *msg, enum log_flags prev,
+static size_t msg_print_text(const struct printk_log *msg,
bool syslog, char *buf, size_t size) { return 0; }
-static size_t cont_print_text(char *text, size_t size) { return 0; }
static bool suppress_message_printing(int level) { return false; }
/* Still needs to be defined for users */
@@ -2296,42 +2213,6 @@ static inline int can_use_console(void)
return cpu_online(raw_smp_processor_id()) || have_callable_console();
}
-static void console_cont_flush(char *text, size_t size)
-{
- unsigned long flags;
- size_t len;
-
- raw_spin_lock_irqsave(&logbuf_lock, flags);
-
- if (!cont.len)
- goto out;
-
- if (suppress_message_printing(cont.level)) {
- cont.cons = cont.len;
- if (cont.flushed)
- cont.len = 0;
- goto out;
- }
-
- /*
- * We still queue earlier records, likely because the console was
- * busy. The earlier ones need to be printed before this one, we
- * did not flush any fragment so far, so just let it queue up.
- */
- if (console_seq < log_next_seq && !cont.cons)
- goto out;
-
- len = cont_print_text(text, size);
- raw_spin_unlock(&logbuf_lock);
- stop_critical_timings();
- call_console_drivers(cont.level, NULL, 0, text, len);
- start_critical_timings();
- local_irq_restore(flags);
- return;
-out:
- raw_spin_unlock_irqrestore(&logbuf_lock, flags);
-}
-
/**
* console_unlock - unlock the console system
*
@@ -2385,9 +2266,6 @@ void console_unlock(void)
return;
}
- /* flush buffered message fragment immediately to console */
- console_cont_flush(text, sizeof(text));
-
for (;;) {
struct printk_log *msg;
size_t ext_len = 0;
@@ -2407,7 +2285,6 @@ void console_unlock(void)
/* messages are gone, move to first one */
console_seq = log_first_seq;
console_idx = log_first_idx;
- console_prev = 0;
} else {
len = 0;
}
@@ -2417,8 +2294,7 @@ void console_unlock(void)
msg = log_from_idx(console_idx);
level = msg->level;
- if ((msg->flags & LOG_NOCONS) ||
- suppress_message_printing(level)) {
+ if (suppress_message_printing(level)) {
/*
* Skip record we have buffered and already printed
* directly to the console when we received it, and
@@ -2426,22 +2302,14 @@ void console_unlock(void)
*/
console_idx = log_next(console_idx);
console_seq++;
- /*
- * We will get here again when we register a new
- * CON_PRINTBUFFER console. Clear the flag so we
- * will properly dump everything later.
- */
- msg->flags &= ~LOG_NOCONS;
- console_prev = msg->flags;
goto skip;
}
- len += msg_print_text(msg, console_prev, false,
- text + len, sizeof(text) - len);
+ len += msg_print_text(msg, false, text + len, sizeof(text) - len);
if (nr_ext_console_drivers) {
ext_len = msg_print_ext_header(ext_text,
sizeof(ext_text),
- msg, console_seq, console_prev);
+ msg, console_seq);
ext_len += msg_print_ext_body(ext_text + ext_len,
sizeof(ext_text) - ext_len,
log_dict(msg), msg->dict_len,
@@ -2449,7 +2317,6 @@ void console_unlock(void)
}
console_idx = log_next(console_idx);
console_seq++;
- console_prev = msg->flags;
raw_spin_unlock(&logbuf_lock);
stop_critical_timings(); /* don't trace print latency */
@@ -2483,7 +2350,7 @@ void console_unlock(void)
if (retry && console_trylock())
goto again;
- if (wake_klogd)
+ if (wake_klogd || cont.len)
wake_up_klogd();
}
EXPORT_SYMBOL(console_unlock);
@@ -2744,7 +2611,6 @@ void register_console(struct console *newcon)
raw_spin_lock_irqsave(&logbuf_lock, flags);
console_seq = syslog_seq;
console_idx = syslog_idx;
- console_prev = syslog_prev;
raw_spin_unlock_irqrestore(&logbuf_lock, flags);
/*
* We're about to replay the log buffer. Only do this to the
@@ -2883,6 +2749,7 @@ static void wake_up_klogd_work_func(struct irq_work *irq_work)
if (pending & PRINTK_PENDING_WAKEUP)
wake_up_interruptible(&log_wait);
+ deferred_cont_flush();
}
static DEFINE_PER_CPU(struct irq_work, wake_up_klogd_work) = {
@@ -3095,7 +2962,7 @@ bool kmsg_dump_get_line_nolock(struct kmsg_dumper *dumper, bool syslog,
goto out;
msg = log_from_idx(dumper->cur_idx);
- l = msg_print_text(msg, 0, syslog, line, size);
+ l = msg_print_text(msg, syslog, line, size);
dumper->cur_idx = log_next(dumper->cur_idx);
dumper->cur_seq++;
@@ -3165,7 +3032,6 @@ bool kmsg_dump_get_buffer(struct kmsg_dumper *dumper, bool syslog,
u32 idx;
u64 next_seq;
u32 next_idx;
- enum log_flags prev;
size_t l = 0;
bool ret = false;
@@ -3189,27 +3055,23 @@ bool kmsg_dump_get_buffer(struct kmsg_dumper *dumper, bool syslog,
/* calculate length of entire buffer */
seq = dumper->cur_seq;
idx = dumper->cur_idx;
- prev = 0;
while (seq < dumper->next_seq) {
struct printk_log *msg = log_from_idx(idx);
- l += msg_print_text(msg, prev, true, NULL, 0);
+ l += msg_print_text(msg, true, NULL, 0);
idx = log_next(idx);
seq++;
- prev = msg->flags;
}
/* move first record forward until length fits into the buffer */
seq = dumper->cur_seq;
idx = dumper->cur_idx;
- prev = 0;
while (l > size && seq < dumper->next_seq) {
struct printk_log *msg = log_from_idx(idx);
- l -= msg_print_text(msg, prev, true, NULL, 0);
+ l -= msg_print_text(msg, true, NULL, 0);
idx = log_next(idx);
seq++;
- prev = msg->flags;
}
/* last message in next interation */
@@ -3220,10 +3082,9 @@ bool kmsg_dump_get_buffer(struct kmsg_dumper *dumper, bool syslog,
while (seq < dumper->next_seq) {
struct printk_log *msg = log_from_idx(idx);
- l += msg_print_text(msg, prev, syslog, buf + l, size - l);
+ l += msg_print_text(msg, syslog, buf + l, size - l);
idx = log_next(idx);
seq++;
- prev = msg->flags;
}
dumper->next_seq = next_seq;
^ permalink raw reply related
* arm/boot/dts/at91sam9260.dtsi USB clock divisors and AT91SAM9G20
From: Andrey Yurovsky @ 2016-10-25 17:49 UTC (permalink / raw)
To: linux-arm-kernel
I'm working at an AT91SAM9G20 on which the USB clock divisor was wrong
and traced the issue down to arm/boot/dts/at91sam9260.dtsi which is
included like this:
at91sam9g20ek_common.dtsi
at91sam9g20.dtsi
at91sam9260.dtsi
This has a node:
usb: usbck {
compatible = "atmel,at91rm9200-clk-usb";
#clock-cells = <0>;
atmel,clk-divisors = <1 2 4 0>;
clocks = <&pllb>;
};
However the G20 parts seem to need a different divisor, for me this works:
usb: usbck {
compatible = "atmel,at91rm9200-clk-usb";
#clock-cells = <0>;
atmel,clk-divisors = <4 2 0 0>;
clocks = <&pllb>;
};
Should the USB clock node be moved to a separate .dtsi file to account
for this difference?
^ permalink raw reply
* [PATCH] ARM: davinci: da850: Fix pwm name matching
From: David Lechner @ 2016-10-25 17:54 UTC (permalink / raw)
To: linux-arm-kernel
This fixes pwm name matching for DA850 familiy devices. When using device
tree, the da850_auxdata_lookup[] table caused pwm devices to have the exact
same name, which caused errors when trying to register the devices.
The names for clock matching in da850_clks[] also have to be updated to
to exactly match in order for the clock lookup to work correctly.
Signed-off-by: David Lechner <david@lechnology.com>
---
Tested working on LEGO MINDSTORMS EV3.
arch/arm/mach-davinci/da850.c | 10 +++++++---
arch/arm/mach-davinci/da8xx-dt.c | 10 +++++-----
2 files changed, 12 insertions(+), 8 deletions(-)
diff --git a/arch/arm/mach-davinci/da850.c b/arch/arm/mach-davinci/da850.c
index ed3d0e9..6b78a8f 100644
--- a/arch/arm/mach-davinci/da850.c
+++ b/arch/arm/mach-davinci/da850.c
@@ -510,9 +510,13 @@ static struct clk_lookup da850_clks[] = {
CLK("vpif", NULL, &vpif_clk),
CLK("ahci_da850", NULL, &sata_clk),
CLK("davinci-rproc.0", NULL, &dsp_clk),
- CLK("ehrpwm", "fck", &ehrpwm_clk),
- CLK("ehrpwm", "tbclk", &ehrpwm_tbclk),
- CLK("ecap", "fck", &ecap_clk),
+ CLK("ehrpwm.0", "fck", &ehrpwm_clk),
+ CLK("ehrpwm.0", "tbclk", &ehrpwm_tbclk),
+ CLK("ehrpwm.1", "fck", &ehrpwm_clk),
+ CLK("ehrpwm.1", "tbclk", &ehrpwm_tbclk),
+ CLK("ecap.0", "fck", &ecap_clk),
+ CLK("ecap.1", "fck", &ecap_clk),
+ CLK("ecap.2", "fck", &ecap_clk),
CLK(NULL, NULL, NULL),
};
diff --git a/arch/arm/mach-davinci/da8xx-dt.c b/arch/arm/mach-davinci/da8xx-dt.c
index 7947267..6ad8ddb 100644
--- a/arch/arm/mach-davinci/da8xx-dt.c
+++ b/arch/arm/mach-davinci/da8xx-dt.c
@@ -23,11 +23,11 @@ static struct of_dev_auxdata da850_auxdata_lookup[] __initdata = {
OF_DEV_AUXDATA("ti,davinci-i2c", 0x01e28000, "i2c_davinci.2", NULL),
OF_DEV_AUXDATA("ti,davinci-wdt", 0x01c21000, "davinci-wdt", NULL),
OF_DEV_AUXDATA("ti,da830-mmc", 0x01c40000, "da830-mmc.0", NULL),
- OF_DEV_AUXDATA("ti,da850-ehrpwm", 0x01f00000, "ehrpwm", NULL),
- OF_DEV_AUXDATA("ti,da850-ehrpwm", 0x01f02000, "ehrpwm", NULL),
- OF_DEV_AUXDATA("ti,da850-ecap", 0x01f06000, "ecap", NULL),
- OF_DEV_AUXDATA("ti,da850-ecap", 0x01f07000, "ecap", NULL),
- OF_DEV_AUXDATA("ti,da850-ecap", 0x01f08000, "ecap", NULL),
+ OF_DEV_AUXDATA("ti,da850-ehrpwm", 0x01f00000, "ehrpwm.0", NULL),
+ OF_DEV_AUXDATA("ti,da850-ehrpwm", 0x01f02000, "ehrpwm.1", NULL),
+ OF_DEV_AUXDATA("ti,da850-ecap", 0x01f06000, "ecap.0", NULL),
+ OF_DEV_AUXDATA("ti,da850-ecap", 0x01f07000, "ecap.1", NULL),
+ OF_DEV_AUXDATA("ti,da850-ecap", 0x01f08000, "ecap.2", NULL),
OF_DEV_AUXDATA("ti,da830-spi", 0x01c41000, "spi_davinci.0", NULL),
OF_DEV_AUXDATA("ti,da830-spi", 0x01f0e000, "spi_davinci.1", NULL),
OF_DEV_AUXDATA("ns16550a", 0x01c42000, "serial8250.0", NULL),
--
2.7.4
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox