* [PATCH 5/10] dt: bindings: Add bindings for Marvell Xenon SD Host Controller
From: Gregory CLEMENT @ 2016-11-24 9:22 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <4031579.CBE32NHUoW@wuerfel>
Hi Arnd,
On jeu., nov. 24 2016, Arnd Bergmann <arnd@arndb.de> wrote:
> On Thursday, November 24, 2016 10:05:45 AM CET Ulf Hansson wrote:
>> > You also mentioned other bindings using child nodes, but for this one
>> > we have one controller with only one set of register with multiple slots
>> > (Atmel is an example). Here each slot have it own set of register.
>> >
>> > Actually giving the fact that each slot is controlled by a different set
>> > of register I wonder why the hardware can't also deduce the slot number
>> > from the address register. For me it looks like an hardware bug but we
>> > have to deal with it.
>> >
>> > Do you still think we needchild node here?
>>
>> Using child-nodes for slots like what's done in the atmel case, is
>> currently broken. I would recommend to avoid using child-nodes for
>> slots, if possible.
>>
>> To give you some more background, currently the mmc core treats child
>> nodes as embedded non-removable cards or SDIO funcs. However, we can
>> change to make child-nodes also allowed to describe slots, but it
>> requires a specific compatible for "slots" and of course then we also
>> need to update the DT parsing of the child-nodes in the mmc core.
>>
>> Documentation/devicetree/bindings/mmc/mmc.txt
>> Documentation/devicetree/bindings/mmc/mmc-card.txt
>
> I don't see anything wrong with having child nodes for the slots
> even with the current binding, under one condition:
>
> The mmc.txt binding above must refer only to the child node, while
> the parent node conceptually becomes a plain bus or MFD that
> happens to encapsulate multiple MMC host controllers, and possibly
> provides some shared registers to them.
I don't have an option for mmc in general, but using child node do not
fit at all the xenon controller.
For this controller each slot has its own set of register, so there is
no common ressource to share so no advantage to use it. Using child node
in our case will just make the code more complex for no benefit.
Gregory
>
> Arnd
--
Gregory Clement, Free Electrons
Kernel, drivers, real-time and embedded Linux
development, consulting, training and support.
http://free-electrons.com
^ permalink raw reply
* [RFC v2: PATCH 1/2] dt-bindings: Document the hi3660 reset bindings
From: Philipp Zabel @ 2016-11-24 9:26 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1479888476-13138-2-git-send-email-zhangfei.gao@linaro.org>
Am Mittwoch, den 23.11.2016, 16:07 +0800 schrieb Zhangfei Gao:
> Add DT bindings documentation for hi3660 SoC reset controller.
>
> Signed-off-by: Zhangfei Gao <zhangfei.gao@linaro.org>
> ---
> .../bindings/reset/hisilicon,hi3660-reset.txt | 51 ++++++++++++++++++++++
> 1 file changed, 51 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
>
> diff --git a/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
> new file mode 100644
> index 0000000..250daf2
> --- /dev/null
> +++ b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
> @@ -0,0 +1,51 @@
> +Hisilicon System Reset Controller
> +======================================
> +
> +Please also refer to reset.txt in this directory for common reset
> +controller binding usage.
> +
> +The reset controller registers are part of the system-ctl block on
> +hi3660 SoC.
> +
> +Required properties:
> +- compatible: should be
> + "hisilicon,hi3660-reset"
> +- #reset-cells: 1, see below
> +- hisi,rst-syscon: phandle of the reset's syscon.
> +- hisi,reset-bits: Contains the reset control register information
> + Should contain 2 cells for each reset exposed to
> + consumers, defined as:
> + Cell #1 : offset from the syscon register base
> + Cell #2 : bits position of the control register
> +
> +Example:
> + iomcu: iomcu at ffd7e000 {
> + compatible = "hisilicon,hi3660-iomcu", "syscon";
> + reg = <0x0 0xffd7e000 0x0 0x1000>;
> + };
> +
> + iomcu_rst: iomcu_rst_controller {
This should be
iomcu_rst: reset-controller {
> + compatible = "hisilicon,hi3660-reset";
> + #reset-cells = <1>;
> + hisi,rst-syscon = <&iomcu>;
> + hisi,reset-bits = <0x20 0x8 /* 0: i2c0 */
> + 0x20 0x10 /* 1: i2c1 */
> + 0x20 0x20 /* 2: i2c2 */
> + 0x20 0x8000000>; /* 3: i2c6 */
> + };
The reset lines are controlled through iomcu bits, is there a reason not
to put the iomcu_rst node inside the iomcu node? That way the
hisi,rst-syscon property could be removed and the syscon could be
retrieved via the reset-controller parent node.
> +Specifying reset lines connected to IP modules
> +==============================================
> +example:
> +
> + i2c0: i2c at ..... {
> + ...
> + resets = <&iomcu_rst 0>;
> + ...
> + };
> +
> + i2c1: i2c at ..... {
> + ...
> + resets = <&iomcu_rst 1>;
> + ...
> + };
regards
Philipp
^ permalink raw reply
* [PATCH v1 & v6 1/2] PM/devfreq: add suspend frequency support
From: Chanwoo Choi @ 2016-11-24 9:28 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <5836A622.20007@rock-chips.com>
Hi Lin,
On 2016? 11? 24? 17:34, hl wrote:
> Hi Chanwoo Choi,
>
>
> On 2016?11?24? 16:16, Chanwoo Choi wrote:
>> Hi Lin,
>>
>> On 2016? 11? 24? 16:34, hl wrote:
>>> Hi Chanwoo Choi,
>>>
>>> I think the dev_pm_opp_get_suspend_opp() have implement most of
>>> the funtion, all we need is just define the node in dts, like following:
>>>
>>> &dmc_opp_table {
>>> opp06 {
>>> opp-suspend;
>>> };
>>> };
>> Two approaches use the 'opp-suspend' property.
>>
>> I think that the method to support suspend-opp have to
>> guarantee following conditions:
>> - Support the all of devfreq's governors.
> As MyungJoo Ham suggestion, i will set the suspend frequency in devfreq_suspend_device(),
> which will ingore governor.
Other approach already support the all of governors.
Before calling the mail, I discussed with Myungjoo Ham.
Myungjoo prefer to use the devfreq_suspend/devfreq_resume().
To Myungjoo,
Please add your opinion how to support the suspend frequency.
>> - Devfreq framework have the responsibility to change the
>> frequency/voltage for suspend-opp. If we uses the
>> new devfreq_suspend(), each devfreq device don't care
>> how to support the suspend-opp. Just the developer of each
>> devfreq device need to add 'opp-suspend' propet to OPP entry in DT file.
> Why should support change the voltage in devfreq framework, i think it shuold be handle in
> specific driver, i think the devfreq only handle it can get the right frequency, then pass it to
No, the frequency should be handled by governor or framework.
The each devfreq device has no any responsibility of next frequency/voltage.
The governor and core of devfreq can decide the next frequency/voltage.
You can refer to the cpufreq subsystem.
> specific driver, i think the voltage should handle in the devfreq->profile->target();
The call of devfreq->profile->target() have to be handled by devfreq framework.
If user want to set the suspend frequency, user can add the 'suspend-opp' property.
It think this way is easy.
But,
If the each devfreq device want to decide the next frequency/voltage only for
suspend state. We can check the cpufreq subsystem.
If specific devfreq device want to handle the suspend frequency,
each devfreq will add the own suspend/resume functions as following:
struct devfreq_dev_profile {
int (*suspend)(struct devfreq *dev); // new function pointer
int (*resume)(struct devfreq *dev); // new function pointer
} a_profile;
a_profile = devfreq_generic_suspend;
The devfreq framework will provide the devfreq_generic_suspend() funticon.
int devfreq_generic_suspend(struce devfreq *dev) {
...
devfreq->profile->target(..., devfreq->suspend_freq);
...
}
or
a_profile = a_devfreq_suspend; // specific function of each devfreq device
The devfreq_suspend() will call 'devfreq->profile->suspend()' function
instead of devfreq->profile->target();
The devfreq call the 'devfreq->profile->suspend()'
to support the suspend frequency.
Regards,
Chanwoo Choi
>> Best Regards,
>> Chanwoo Choi
>>
>>> so i think my way semm more simple.
>>>
>>> On 2016?11?24? 15:10, Chanwoo Choi wrote:
>>>> + Tobias Jakobi,
>>>>
>>>> Hi Lin,
>>>>
>>>> We need to discuss how to support the suspend-opp of devfreq device.
>>>> Now, there are two patch thread for suspend-opp of devfreq.
>>>>
>>>> The Lin's approach modify the devfreq_suspend_device() to support suspend-opp.
>>>> The Tobias's approach[1] add new devfreq_suspend() and then call it on dpm_suspend()
>>>> when entering the suspend state.
>>>>
>>>> [1] [RFC 0/4] PM / devfreq: draft for OPP suspend impl
>>>> - https://patchwork.kernel.org/patch/9443323/
>>>> - https://patchwork.kernel.org/patch/9443325/
>>>> - https://patchwork.kernel.org/patch/9443329/
>>>> - https://patchwork.kernel.org/patch/9443331/
>>>>
>>>> I think we need to discuss it together.
>>>>
>>>> Regards,
>>>> Chanwoo Choi
>>>>
>>>> On 2016? 11? 24? 15:45, hl wrote:
>>>>> Hi MyungJoo Ham,
>>>>>
>>>>> On 2016?11?24? 14:14, MyungJoo Ham wrote:
>>>>>> On Thu, Nov 24, 2016 at 11:18 AM, hl <hl@rock-chips.com> wrote:
>>>>>>> Hi MyungJoo Ham,
>>>>>> []
>>>>>>>> We still need to sync the all status even i call target() in
>>>>>>>> devfreq_suspend/resume_device
>>>>>>>> directly, so still need update_devfreq() other setp except
>>>>>>>> devfreq->governor->get_target_freq(devfreq, &freq);
>>>>>>> And i think it better to be governor behaviors, for userspace they may not
>>>>>>> want to change
>>>>>>> the suspend frequency like other governor, the frequency should decide by
>>>>>>> the user, if they
>>>>>>> want this function, they should like other governor to rigister a
>>>>>>> devfreq_monitor_suspend().
>>>>>>> What do you think about my rev6 patch?
>>>>>> If I understand the intention correctly, this is for the stability of
>>>>>> the device due to the behavior or bootloader/SoC-initializer, which
>>>>>> has nothing to do with governors.
>>>>>>
>>>>>> Even if users are using userspace, as long as they set the custom
>>>>>> frequencies lower than the default, they have the possibility of
>>>>>> being unstable as ondemand is going to have.
>>>>>>
>>>>>>
>>>>>> To reuse the update_devfreq() code, you may do something like:
>>>>>>
>>>>>> static int _update_freq(struct devfreq *devfreq, bool is_suspending)
>>>>>> {
>>>>>> /* original contents of update_freq with if statement with is_suspending wrapping get_target_freq */
>>>>>> }
>>>>>> int update_freq(struct devfreq *devfreq)
>>>>>> {
>>>>>> return _update_freq(devfreq, false);
>>>>>> }
>>>>>>
>>>>>>
>>>>>> There should be other good non-invasive methods that are not governoe-specific as well.
>>>>>>
>>>>> Thanks for your suggestion, i will update the new version soon.
>>>>>> Cheers,
>>>>>> MyungJoo
>>>>>>
>>>>>>
>>>>>>
>>>>>>
>>>>>> _______________________________________________
>>>>>> Linux-rockchip mailing list
>>>>>> Linux-rockchip at lists.infradead.org
>>>>>> http://lists.infradead.org/mailman/listinfo/linux-rockchip
>>>>> --
>>>>> Lin Huang
>>>>>
>>>>
>>>>
>>
>>
>>
>
--
Best Regards,
Chanwoo Choi
^ permalink raw reply
* reboot fails on at91sam9g20 with kernel 4.x
From: Alexander Dahl @ 2016-11-24 9:29 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161123221121.pkkhwhgqig5elwa7@piout.net>
Hei hei,
Am Mittwoch, 23. November 2016, 23:11:21 schrieb Alexandre Belloni:
> Since 3.18, the shdwc and reset controller have their own drivers that
> may or may not be compiled in the kernel. Can you check you have
> CONFIG_POWER_RESET_AT91_POWEROFF and CONFIG_POWER_RESET_AT91_RESET
> set in your configuration? Also, you probably want to check the DT
> definition of the shdwc and the rstc.
You were right, those were not set.
-# CONFIG_POWER_RESET is not set
+CONFIG_POWER_RESET=y
+CONFIG_POWER_RESET_AT91_POWEROFF=y
+CONFIG_POWER_RESET_AT91_RESET=y
With the above change in the kernel config the board reboots fine.
I'm not quite sure anymore how I got to my kernelconfig, maybe based on
a pre 3.18 config without going through oldconfig.
I double checked the at91_dt_defconfig from 4.8.10 now and it activates
those options, maybe I should have done this in the first place.
So thank you very much for your hint. :-)
Greets
Alex
--
------------------------------------------------------------------------
Thorsis Technologies GmbH Tel.: +49-391-544 563-3036
Oststra?e 18 Fax.: +49-391-544 563-9099
39114 Magdeburg http://www.thorsis.com/
Sitz der Gesellschaft: Magdeburg
Amtsgericht Stendal HRB 110339
Gesch?ftsf?hrer: Dipl.-Ing. Thorsten Szczepanski
------------------------------------------------------------------------
^ permalink raw reply
* [PATCH] ARM: fix kmemleak for XIP_KERNEL
From: Jakub Kicinski @ 2016-11-24 9:30 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161122142829.1776129-1-arnd@arndb.de>
On Tue, Nov 22, 2016 at 6:28 AM, Arnd Bergmann <arnd@arndb.de> wrote:
> The newly added check for RO_AFTER_INIT_DATA in kmemleak breaks ARM whenever
> XIP_KERNEL is enabled:
>
> mm/kmemleak.o: In function `kmemleak_scan':
> kmemleak.c:(.text.kmemleak_scan+0x2e4): undefined reference to `__end_data_ro_after_init'
> kmemleak.c:(.text.kmemleak_scan+0x2e8): undefined reference to `__start_data_ro_after_init'
>
> This adds the start/end symbols for the section even in the case of having
> no data in the section, to make the check work while keeping the architecture
> specific override in one place.
>
> Fixes: d7c19b066dcf ("mm: kmemleak: scan .data.ro_after_init")
> Signed-off-by: Arnd Bergmann <arnd@arndb.de>
> ---
> The patch causing this was merged late into v4.9-rc, this one should
> probably go there as well.
>
> I assume the same problem exists on s390, but I have not checked that.
Hi Arnd!
Sorry for breaking things again :( The confusion must have been caused
by going via different trees. Actually, Russell's commit is dated 6
days after mine so could as well be:
Fixes: 2a3811068fbc ("ARM: Fix XIP kernels")
Not that it matters.
About s390 - I thought I took care of it in d7c19b066dcf ("mm:
kmemleak: scan .data.ro_after_init"), do you see anything suspicious
in the way I did it? I'll do some more s390 builds just to triple
check.
Sorry again,
Kuba
^ permalink raw reply
* [RFC PATCH 2/5] dmaengine: allow sun6i-dma for more SoCs
From: Chen-Yu Tsai @ 2016-11-24 9:30 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <34b5e50f-a091-9bd8-7a74-96e538a7351d@arm.com>
On Thu, Nov 24, 2016 at 5:16 PM, Andre Przywara <andre.przywara@arm.com> wrote:
> Hi,
>
> On 24/11/16 04:16, Chen-Yu Tsai wrote:
>> Hi,
>>
>> On Thu, Nov 24, 2016 at 9:17 AM, Andre Przywara <andre.przywara@arm.com> wrote:
>>> The sun6i DMA driver is used in the Allwinner A64 and H5 SoC, which
>>> have arm64 capable cores. Add the generic sunxi config symbol to allow
>>> the driver to be selected by arm64 Kconfigs, which don't feature
>>> SoC specific MACH_xxxx configs.
>>>
>>> Signed-off-by: Andre Przywara <andre.przywara@arm.com>
>>> ---
>>> drivers/dma/Kconfig | 2 +-
>>> 1 file changed, 1 insertion(+), 1 deletion(-)
>>>
>>> diff --git a/drivers/dma/Kconfig b/drivers/dma/Kconfig
>>> index af63a6b..003c284 100644
>>> --- a/drivers/dma/Kconfig
>>> +++ b/drivers/dma/Kconfig
>>> @@ -157,7 +157,7 @@ config DMA_SUN4I
>>>
>>> config DMA_SUN6I
>>> tristate "Allwinner A31 SoCs DMA support"
>>> - depends on MACH_SUN6I || MACH_SUN8I || COMPILE_TEST
>>> + depends on MACH_SUN6I || MACH_SUN8I || COMPILE_TEST || ARCH_SUNXI
>>
>> AFAIK ARCH_SUNXI encompasses/supersedes MACH_SUN*I.
>> (And I don't have to add MACH_SUN9I later :) )
>
> Sure, admittedly it was just a quick hack to get things going.
> Actually I don't know why we had a *depend* on those MACH_s before. I
> think technically it does not depend on a certain SoC (having the
> COMPILE_TEST in there hints on that). So what about:
It was really because this DMA engine only comes with the later
SoCs. We have dma-sun4i for the older one. But yes, there's no
reason why you can't build it for the earlier SoC. It just doesn't
get used.
>
> depends on ARCH_SUNXI || COMPILE_TEST
>
> and maybe:
>
> default y if MACH_SUN6I || MACH_SUN8I
>
> Though I see that both multi_v7_defconfig and sunxi_defconfig explicitly
> set this, so this wouldn't be needed?
I guess it's just nice to get stuff out of defconfig?
Why not go all the way and just have
default y if ARCH_SUNXI
ChenYu
>
> Cheers,
> Andre.
^ permalink raw reply
* [PATCH] ARM: dts: da850: enable the memctrl and mstpri nodes per board
From: Bartosz Golaszewski @ 2016-11-24 9:31 UTC (permalink / raw)
To: linux-arm-kernel
Currently the memory controller and master priorities drivers are
enabled in da850.dtsi. For boards for which there are no settings
defined, this makes these drivers emit error messages.
Disable the nodes in da850.dtsi and only enable them for da850-lcdk -
the only board that currently needs them.
Signed-off-by: Bartosz Golaszewski <bgolaszewski@baylibre.com>
---
arch/arm/boot/dts/da850-lcdk.dts | 8 ++++++++
arch/arm/boot/dts/da850.dtsi | 2 ++
2 files changed, 10 insertions(+)
diff --git a/arch/arm/boot/dts/da850-lcdk.dts b/arch/arm/boot/dts/da850-lcdk.dts
index 3b99a88..94504c8 100644
--- a/arch/arm/boot/dts/da850-lcdk.dts
+++ b/arch/arm/boot/dts/da850-lcdk.dts
@@ -283,3 +283,11 @@
&display {
status = "okay";
};
+
+&prictrl {
+ status = "okay";
+};
+
+&memctrl {
+ status = "okay";
+};
diff --git a/arch/arm/boot/dts/da850.dtsi b/arch/arm/boot/dts/da850.dtsi
index 36066fa..4e40187 100644
--- a/arch/arm/boot/dts/da850.dtsi
+++ b/arch/arm/boot/dts/da850.dtsi
@@ -212,6 +212,7 @@
prictrl: priority-controller at 14110 {
compatible = "ti,da850-mstpri";
reg = <0x14110 0x0c>;
+ status = "disabled";
};
cfgchip: chip-controller at 1417c {
compatible = "ti,da830-cfgchip", "syscon", "simple-mfd";
@@ -457,5 +458,6 @@
memctrl: memory-controller at b0000000 {
compatible = "ti,da850-ddr-controller";
reg = <0xb0000000 0xe8>;
+ status = "disabled";
};
};
--
2.9.3
^ permalink raw reply related
* [PATCH 5/10] dt: bindings: Add bindings for Marvell Xenon SD Host Controller
From: Arnd Bergmann @ 2016-11-24 9:34 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <877f7tmduw.fsf@free-electrons.com>
On Thursday, November 24, 2016 10:22:31 AM CET Gregory CLEMENT wrote:
>
> I don't have an option for mmc in general, but using child node do not
> fit at all the xenon controller.
>
> For this controller each slot has its own set of register, so there is
> no common ressource to share so no advantage to use it. Using child node
> in our case will just make the code more complex for no benefit.
If every slot has its own registers, what is it that makes up the
'controller'? It sounds to me that you just have to adjust the terminology
and talk about multiple controllers then, with one slot per controller.
Arnd
^ permalink raw reply
* [RFC PATCH v2 1/2] macb: Add 1588 support in Cadence GEM.
From: Andrei.Pistirica at microchip.com @ 2016-11-24 9:36 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161123210318.GB2845@localhost.localdomain>
> -----Original Message-----
> From: Richard Cochran [mailto:richardcochran at gmail.com]
> Sent: Wednesday, November 23, 2016 11:03 PM
> To: Andrei Pistirica - M16132
> Cc: netdev at vger.kernel.org; linux-kernel at vger.kernel.org; linux-arm-
> kernel at lists.infradead.org; davem at davemloft.net;
> nicolas.ferre at atmel.com; harinikatakamlinux at gmail.com;
> harini.katakam at xilinx.com; punnaia at xilinx.com; michals at xilinx.com;
> anirudh at xilinx.com; boris.brezillon at free-electrons.com;
> alexandre.belloni at free-electrons.com; tbultel at pixelsurmer.com
> Subject: Re: [RFC PATCH v2 1/2] macb: Add 1588 support in Cadence GEM.
>
> On Wed, Nov 23, 2016 at 02:34:03PM +0100, Andrei Pistirica wrote:
> > From what I understand, your suggestion is:
> > (ns | frac) * ppb = (total_ns | total_frac) (total_ns | total_frac) /
> > 10^9 = (adj_ns | adj_frac) This is correct iff total_ns/10^9 >= 1, but
> > the problem is that there are missed fractions due to the following
> > approximation:
> > frac*ppb =~
> > (ns*ppb+frac*ppb*2^16)*2^16-10^9*2^16*flor(ns*ppb+frac*ppb*2^16,
> > 10^9).
>
> -ENOPARSE;
>
> > An example which uses values from a real test:
> > let ppb=4891, ns=12 and frac=3158
>
> That is a very strange example for nominal frequency. The clock period is
> 12.048187255859375 nanoseconds, and so the frequency is
> 83000037.99 Hz.
>
> But hey, let's go with it...
>
> > - using suggested algorithm, yields: adj_ns = 0 and adj_frac = 0
> > - using in-place algorithm, yields: adj_ns = 0, adj_frac = 4 You can
> > check the calculus.
>
> The test program, below, shows you what I meant. (Of course, you should
> adjust this to fit the adjfine() method.)
>
> Unfortunately, this device has a very coarse frequency resolution.
> Using a nominal period of ns=12 as an example, the resolution is
> 2^-16 / 12 or 1.27 ppm. The 24 bit device is much better in this repect.
>
> The output using your example numbers is:
>
> $ ./a.out 12 3158 4891
> ns=12 frac=3158
> ns=12 frac=3162
>
> $ ./a.out 12 3158 -4891
> ns=12 frac=3158
> ns=12 frac=3154
>
> See how you get a result of +/- 4 with just one division?
>
> Thanks,
> Richard
>
> ---
> #include <stdint.h>
> #include <stdio.h>
> #include <stdlib.h>
>
> static void adjfreq(uint32_t ns, uint32_t frac, int32_t ppb) {
> uint64_t adj;
> uint32_t diff, word;
> int neg_adj = 0;
>
> printf("ns=%u frac=%u\n", ns, frac);
>
> if (ppb < 0) {
> neg_adj = 1;
> ppb = -ppb;
> }
> word = (ns << 16) + frac;
> adj = word;
> adj *= ppb;
> adj += 500000000UL;
> diff = adj / 1000000000UL;
>
> word = neg_adj ? word - diff : word + diff;
> printf("ns=%u frac=%u\n", word >> 16, word & 0xffff); }
>
> int main(int argc, char *argv[])
> {
> uint32_t ns, frac;
> int32_t ppb;
>
> if (argc != 4) {
> puts("need ns, frac, and ppb");
> return -1;
> }
> ns = atoi(argv[1]);
> frac = atoi(argv[2]);
> ppb = atoi(argv[3]);
> adjfreq(ns, frac, ppb);
> return 0;
> }
Ok, thanks.
I will use this one then.
Regards,
Andrei
^ permalink raw reply
* [PATCH 7/9] clocksource/drivers/rockchip_timer: implement clocksource timer
From: Alexander Kochetkov @ 2016-11-24 9:36 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1479922177-20136-7-git-send-email-al.kochet@gmail.com>
> In order to use the patch you have to setup the timer using
> 'rockchip,clocksource' device tree property
Just came in mind, that it is better to replace 'rockchip,clocksource' device tree property
with KConfig option in order to enable clocksource on dedicated timer?
Someting like:
[ ] enable clocksource
clocksource timer name:
Any feedback would be appreciated.
Alexander.
^ permalink raw reply
* [PATCH] ARM: fix kmemleak for XIP_KERNEL
From: Arnd Bergmann @ 2016-11-24 9:37 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CAJpBn1zow6P5MUFP+jbOXafoH9dLV8Ng7cJqfRsE8FMEEe9J8Q@mail.gmail.com>
On Thursday, November 24, 2016 1:30:03 AM CET Jakub Kicinski wrote:
> On Tue, Nov 22, 2016 at 6:28 AM, Arnd Bergmann <arnd@arndb.de> wrote:
> > The newly added check for RO_AFTER_INIT_DATA in kmemleak breaks ARM whenever
> > XIP_KERNEL is enabled:
> >
> > mm/kmemleak.o: In function `kmemleak_scan':
> > kmemleak.c:(.text.kmemleak_scan+0x2e4): undefined reference to `__end_data_ro_after_init'
> > kmemleak.c:(.text.kmemleak_scan+0x2e8): undefined reference to `__start_data_ro_after_init'
> >
> > This adds the start/end symbols for the section even in the case of having
> > no data in the section, to make the check work while keeping the architecture
> > specific override in one place.
> >
> > Fixes: d7c19b066dcf ("mm: kmemleak: scan .data.ro_after_init")
> > Signed-off-by: Arnd Bergmann <arnd@arndb.de>
> > ---
> > The patch causing this was merged late into v4.9-rc, this one should
> > probably go there as well.
> >
> > I assume the same problem exists on s390, but I have not checked that.
>
> Hi Arnd!
>
> Sorry for breaking things again :( The confusion must have been caused
> by going via different trees. Actually, Russell's commit is dated 6
> days after mine so could as well be:
>
> Fixes: 2a3811068fbc ("ARM: Fix XIP kernels")
>
> Not that it matters.
Got it. I guess it's really the combination of the two, so I'd clarify
that in the changelog and list both commits.
> About s390 - I thought I took care of it in d7c19b066dcf ("mm:
> kmemleak: scan .data.ro_after_init"), do you see anything suspicious
> in the way I did it? I'll do some more s390 builds just to triple
> check.
You are right, I had already noticed that too but not replied yet.
s390 is ok as far as I can tell.
Arnd
^ permalink raw reply
* [RFC v2: PATCH 1/2] dt-bindings: Document the hi3660 reset bindings
From: zhangfei @ 2016-11-24 9:40 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1479979605.2472.4.camel@pengutronix.de>
On 2016?11?24? 17:26, Philipp Zabel wrote:
> Am Mittwoch, den 23.11.2016, 16:07 +0800 schrieb Zhangfei Gao:
>> Add DT bindings documentation for hi3660 SoC reset controller.
>>
>> Signed-off-by: Zhangfei Gao <zhangfei.gao@linaro.org>
>> ---
>> .../bindings/reset/hisilicon,hi3660-reset.txt | 51 ++++++++++++++++++++++
>> 1 file changed, 51 insertions(+)
>> create mode 100644 Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
>>
>> diff --git a/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
>> new file mode 100644
>> index 0000000..250daf2
>> --- /dev/null
>> +++ b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
>> @@ -0,0 +1,51 @@
>> +Hisilicon System Reset Controller
>> +======================================
>> +
>> +Please also refer to reset.txt in this directory for common reset
>> +controller binding usage.
>> +
>> +The reset controller registers are part of the system-ctl block on
>> +hi3660 SoC.
>> +
>> +Required properties:
>> +- compatible: should be
>> + "hisilicon,hi3660-reset"
>> +- #reset-cells: 1, see below
>> +- hisi,rst-syscon: phandle of the reset's syscon.
>> +- hisi,reset-bits: Contains the reset control register information
>> + Should contain 2 cells for each reset exposed to
>> + consumers, defined as:
>> + Cell #1 : offset from the syscon register base
>> + Cell #2 : bits position of the control register
>> +
>> +Example:
>> + iomcu: iomcu at ffd7e000 {
>> + compatible = "hisilicon,hi3660-iomcu", "syscon";
>> + reg = <0x0 0xffd7e000 0x0 0x1000>;
>> + };
>> +
>> + iomcu_rst: iomcu_rst_controller {
> This should be
> iomcu_rst: reset-controller {
>
>> + compatible = "hisilicon,hi3660-reset";
>> + #reset-cells = <1>;
>> + hisi,rst-syscon = <&iomcu>;
>> + hisi,reset-bits = <0x20 0x8 /* 0: i2c0 */
>> + 0x20 0x10 /* 1: i2c1 */
>> + 0x20 0x20 /* 2: i2c2 */
>> + 0x20 0x8000000>; /* 3: i2c6 */
>> + };
> The reset lines are controlled through iomcu bits, is there a reason not
> to put the iomcu_rst node inside the iomcu node? That way the
> hisi,rst-syscon property could be removed and the syscon could be
> retrieved via the reset-controller parent node.
iomcu is common registers, controls clock and reset, etc.
So we use syscon, without mapping the registers everywhere.
It is common case in hisilicon, same in hi6220.
Also the #clock-cells and #reset-cells can not be put in the same node,
if they are both using probe, since reset_probe will not be called.
So we use hisi,rst-syscon as a general solution.
Thanks
^ permalink raw reply
* [PATCH 5/10] dt: bindings: Add bindings for Marvell Xenon SD Host Controller
From: Thomas Petazzoni @ 2016-11-24 9:48 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <8737ihmctr.fsf@free-electrons.com>
Hello,
On Thu, 24 Nov 2016 10:44:48 +0100, Gregory CLEMENT wrote:
> "A single Xenon IP can support multiple slots.
> Each slot acts as an independent SDHC. It owns independent resources, such
> as register sets clock and PHY.
> Each slot should have an independent device tree node."
I think this wording is still very confusing, and continues to cause
confusion.
We should just state that each Xenon controller supports a single slot,
and that's it.
The text still says "a single Xenon IP can support multiple slots",
which continues to cause confusion.
Best regards,
Thomas
--
Thomas Petazzoni, CTO, Free Electrons
Embedded Linux and Kernel engineering
http://free-electrons.com
^ permalink raw reply
* [PATCH 5/10] dt: bindings: Add bindings for Marvell Xenon SD Host Controller
From: Marcin Wojtas @ 2016-11-24 9:49 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <8737ihmctr.fsf@free-electrons.com>
Hi Gregory,
2016-11-24 10:44 GMT+01:00 Gregory CLEMENT <gregory.clement@free-electrons.com>:
> Hi Arnd,
>
> On jeu., nov. 24 2016, Arnd Bergmann <arnd@arndb.de> wrote:
>
>> On Thursday, November 24, 2016 10:22:31 AM CET Gregory CLEMENT wrote:
>>>
>>> I don't have an option for mmc in general, but using child node do not
>>> fit at all the xenon controller.
>>>
>>> For this controller each slot has its own set of register, so there is
>>> no common ressource to share so no advantage to use it. Using child node
>>> in our case will just make the code more complex for no benefit.
>>
>> If every slot has its own registers, what is it that makes up the
>> 'controller'? It sounds to me that you just have to adjust the terminology
>> and talk about multiple controllers then, with one slot per controller.
>>
>
> I agree and actually there were some words about in at the begining of
> the binding:
>
> "A single Xenon IP can support multiple slots.
> Each slot acts as an independent SDHC. It owns independent resources, such
> as register sets clock and PHY.
> Each slot should have an independent device tree node."
>
> All the confusion came from the fact that we still need to identify a
> slot ID. For an obscure reason the hardware can't guess the slot ID from
> the address register."
>
How about to avoid confusion, by simply renaming this number to
port-id/xenon-id or anything else but slot? I guess this may allow to
avoid some misunderstandings.
Best regards,
Marcin
^ permalink raw reply
* [RFC v2: PATCH 1/2] dt-bindings: Document the hi3660 reset bindings
From: Philipp Zabel @ 2016-11-24 9:50 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <ac3c8e65-e4f2-3a9d-452c-f270d245cf9d@linaro.org>
Am Donnerstag, den 24.11.2016, 17:40 +0800 schrieb zhangfei:
>
> On 2016?11?24? 17:26, Philipp Zabel wrote:
> > Am Mittwoch, den 23.11.2016, 16:07 +0800 schrieb Zhangfei Gao:
> >> Add DT bindings documentation for hi3660 SoC reset controller.
> >>
> >> Signed-off-by: Zhangfei Gao <zhangfei.gao@linaro.org>
> >> ---
> >> .../bindings/reset/hisilicon,hi3660-reset.txt | 51 ++++++++++++++++++++++
> >> 1 file changed, 51 insertions(+)
> >> create mode 100644 Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
> >>
> >> diff --git a/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
> >> new file mode 100644
> >> index 0000000..250daf2
> >> --- /dev/null
> >> +++ b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt
> >> @@ -0,0 +1,51 @@
> >> +Hisilicon System Reset Controller
> >> +======================================
> >> +
> >> +Please also refer to reset.txt in this directory for common reset
> >> +controller binding usage.
> >> +
> >> +The reset controller registers are part of the system-ctl block on
> >> +hi3660 SoC.
> >> +
> >> +Required properties:
> >> +- compatible: should be
> >> + "hisilicon,hi3660-reset"
> >> +- #reset-cells: 1, see below
> >> +- hisi,rst-syscon: phandle of the reset's syscon.
> >> +- hisi,reset-bits: Contains the reset control register information
> >> + Should contain 2 cells for each reset exposed to
> >> + consumers, defined as:
> >> + Cell #1 : offset from the syscon register base
> >> + Cell #2 : bits position of the control register
> >> +
> >> +Example:
> >> + iomcu: iomcu at ffd7e000 {
> >> + compatible = "hisilicon,hi3660-iomcu", "syscon";
> >> + reg = <0x0 0xffd7e000 0x0 0x1000>;
> >> + };
> >> +
> >> + iomcu_rst: iomcu_rst_controller {
> > This should be
> > iomcu_rst: reset-controller {
> >
> >> + compatible = "hisilicon,hi3660-reset";
> >> + #reset-cells = <1>;
> >> + hisi,rst-syscon = <&iomcu>;
> >> + hisi,reset-bits = <0x20 0x8 /* 0: i2c0 */
> >> + 0x20 0x10 /* 1: i2c1 */
> >> + 0x20 0x20 /* 2: i2c2 */
> >> + 0x20 0x8000000>; /* 3: i2c6 */
> >> + };
> > The reset lines are controlled through iomcu bits, is there a reason not
> > to put the iomcu_rst node inside the iomcu node? That way the
> > hisi,rst-syscon property could be removed and the syscon could be
> > retrieved via the reset-controller parent node.
> iomcu is common registers, controls clock and reset, etc.
> So we use syscon, without mapping the registers everywhere.
> It is common case in hisilicon, same in hi6220.
>
> Also the #clock-cells and #reset-cells can not be put in the same node,
> if they are both using probe, since reset_probe will not be called.
>
> So we use hisi,rst-syscon as a general solution.
What I meant is this:
iomcu: iomcu at ffd7e000 {
compatible = "hisilicon,hi3660-iomcu", "syscon", "simple-mfd";
reg = <0x0 0xffd7e000 0x0 0x1000>;
iomcu_rst: reset-controller {
compatible = "hisilicon,hi3660-reset";
#reset-cells = <1>;
hisi,reset-bits = <0x20 0x8 /* 0: i2c0 */
0x20 0x10 /* 1: i2c1 */
0x20 0x20 /* 2: i2c2 */
0x20 0x8000000>; /* 3: i2c6 */
};
};
regards
Philipp
^ permalink raw reply
* [PATCH v1 & v6 1/2] PM/devfreq: add suspend frequency support
From: Chanwoo Choi @ 2016-11-24 9:54 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <5836B2C2.6090308@samsung.com>
Hi Lin,
On 2016? 11? 24? 18:28, Chanwoo Choi wrote:
> Hi Lin,
>
> On 2016? 11? 24? 17:34, hl wrote:
>> Hi Chanwoo Choi,
>>
>>
>> On 2016?11?24? 16:16, Chanwoo Choi wrote:
>>> Hi Lin,
>>>
>>> On 2016? 11? 24? 16:34, hl wrote:
>>>> Hi Chanwoo Choi,
>>>>
>>>> I think the dev_pm_opp_get_suspend_opp() have implement most of
>>>> the funtion, all we need is just define the node in dts, like following:
>>>>
>>>> &dmc_opp_table {
>>>> opp06 {
>>>> opp-suspend;
>>>> };
>>>> };
>>> Two approaches use the 'opp-suspend' property.
>>>
>>> I think that the method to support suspend-opp have to
>>> guarantee following conditions:
>>> - Support the all of devfreq's governors.
>> As MyungJoo Ham suggestion, i will set the suspend frequency in devfreq_suspend_device(),
>> which will ingore governor.
>
> Other approach already support the all of governors.
> Before calling the mail, I discussed with Myungjoo Ham.
> Myungjoo prefer to use the devfreq_suspend/devfreq_resume().
It is not correct expression. We need to wait the reply from Myungjoo
to clarify this.
>
> To Myungjoo,
> Please add your opinion how to support the suspend frequency.
>
>>> - Devfreq framework have the responsibility to change the
>>> frequency/voltage for suspend-opp. If we uses the
>>> new devfreq_suspend(), each devfreq device don't care
>>> how to support the suspend-opp. Just the developer of each
>>> devfreq device need to add 'opp-suspend' propet to OPP entry in DT file.
>> Why should support change the voltage in devfreq framework, i think it shuold be handle in
>> specific driver, i think the devfreq only handle it can get the right frequency, then pass it to
>
> No, the frequency should be handled by governor or framework.
> The each devfreq device has no any responsibility of next frequency/voltage.
> The governor and core of devfreq can decide the next frequency/voltage.
> You can refer to the cpufreq subsystem.
>
>> specific driver, i think the voltage should handle in the devfreq->profile->target();
>
> The call of devfreq->profile->target() have to be handled by devfreq framework.
> If user want to set the suspend frequency, user can add the 'suspend-opp' property.
> It think this way is easy.
>
> But,
> If the each devfreq device want to decide the next frequency/voltage only for
> suspend state. We can check the cpufreq subsystem.
>
> If specific devfreq device want to handle the suspend frequency,
> each devfreq will add the own suspend/resume functions as following:
>
> struct devfreq_dev_profile {
> int (*suspend)(struct devfreq *dev); // new function pointer
> int (*resume)(struct devfreq *dev); // new function pointer
> } a_profile;
>
> a_profile = devfreq_generic_suspend;
>
> The devfreq framework will provide the devfreq_generic_suspend() funticon.
> int devfreq_generic_suspend(struce devfreq *dev) {
> ...
> devfreq->profile->target(..., devfreq->suspend_freq);
> ...
> }
>
> or
>
> a_profile = a_devfreq_suspend; // specific function of each devfreq device
>
> The devfreq_suspend() will call 'devfreq->profile->suspend()' function
> instead of devfreq->profile->target();
>
> The devfreq call the 'devfreq->profile->suspend()'
> to support the suspend frequency.
>
> Regards,
> Chanwoo Choi
The key difference between two approaches:
Your approach:
- The each developer should add the 'opp-suspend' property to the dts file.
- The each devfreq should call the devfreq_suspend_device()
to support the suspend frequency.
If each devfreq doesn't call the devfreq_suspend_device(), devfreq framework
can support the suspend frequency.
Other approach:
- The each developer only should add the 'opp-suspend' property to the dts file
without the additional behavior.
In the cpufreq subsystem,
When support the suspend frequency of cpufreq, we just add 'opp-suspend' property
without the additional behavior.
Regards,
Chanwoo Choi
>
>>> Best Regards,
>>> Chanwoo Choi
>>>
>>>> so i think my way semm more simple.
>>>>
>>>> On 2016?11?24? 15:10, Chanwoo Choi wrote:
>>>>> + Tobias Jakobi,
>>>>>
>>>>> Hi Lin,
>>>>>
>>>>> We need to discuss how to support the suspend-opp of devfreq device.
>>>>> Now, there are two patch thread for suspend-opp of devfreq.
>>>>>
>>>>> The Lin's approach modify the devfreq_suspend_device() to support suspend-opp.
>>>>> The Tobias's approach[1] add new devfreq_suspend() and then call it on dpm_suspend()
>>>>> when entering the suspend state.
>>>>>
>>>>> [1] [RFC 0/4] PM / devfreq: draft for OPP suspend impl
>>>>> - https://patchwork.kernel.org/patch/9443323/
>>>>> - https://patchwork.kernel.org/patch/9443325/
>>>>> - https://patchwork.kernel.org/patch/9443329/
>>>>> - https://patchwork.kernel.org/patch/9443331/
>>>>>
>>>>> I think we need to discuss it together.
>>>>>
>>>>> Regards,
>>>>> Chanwoo Choi
>>>>>
>>>>> On 2016? 11? 24? 15:45, hl wrote:
>>>>>> Hi MyungJoo Ham,
>>>>>>
>>>>>> On 2016?11?24? 14:14, MyungJoo Ham wrote:
>>>>>>> On Thu, Nov 24, 2016 at 11:18 AM, hl <hl@rock-chips.com> wrote:
>>>>>>>> Hi MyungJoo Ham,
>>>>>>> []
>>>>>>>>> We still need to sync the all status even i call target() in
>>>>>>>>> devfreq_suspend/resume_device
>>>>>>>>> directly, so still need update_devfreq() other setp except
>>>>>>>>> devfreq->governor->get_target_freq(devfreq, &freq);
>>>>>>>> And i think it better to be governor behaviors, for userspace they may not
>>>>>>>> want to change
>>>>>>>> the suspend frequency like other governor, the frequency should decide by
>>>>>>>> the user, if they
>>>>>>>> want this function, they should like other governor to rigister a
>>>>>>>> devfreq_monitor_suspend().
>>>>>>>> What do you think about my rev6 patch?
>>>>>>> If I understand the intention correctly, this is for the stability of
>>>>>>> the device due to the behavior or bootloader/SoC-initializer, which
>>>>>>> has nothing to do with governors.
>>>>>>>
>>>>>>> Even if users are using userspace, as long as they set the custom
>>>>>>> frequencies lower than the default, they have the possibility of
>>>>>>> being unstable as ondemand is going to have.
>>>>>>>
>>>>>>>
>>>>>>> To reuse the update_devfreq() code, you may do something like:
>>>>>>>
>>>>>>> static int _update_freq(struct devfreq *devfreq, bool is_suspending)
>>>>>>> {
>>>>>>> /* original contents of update_freq with if statement with is_suspending wrapping get_target_freq */
>>>>>>> }
>>>>>>> int update_freq(struct devfreq *devfreq)
>>>>>>> {
>>>>>>> return _update_freq(devfreq, false);
>>>>>>> }
>>>>>>>
>>>>>>>
>>>>>>> There should be other good non-invasive methods that are not governoe-specific as well.
>>>>>>>
>>>>>> Thanks for your suggestion, i will update the new version soon.
>>>>>>> Cheers,
>>>>>>> MyungJoo
>>>>>>>
>>>>>>>
>>>>>>>
>>>>>>>
>>>>>>> _______________________________________________
>>>>>>> Linux-rockchip mailing list
>>>>>>> Linux-rockchip at lists.infradead.org
>>>>>>> http://lists.infradead.org/mailman/listinfo/linux-rockchip
>>>>>> --
>>>>>> Lin Huang
>>>>>>
>>>>>
>>>>>
>>>
>>>
>>>
>>
>
>
--
Best Regards,
Chanwoo Choi
^ permalink raw reply
* [PATCH v28 0/9] arm64: add kdump support
From: AKASHI Takahiro @ 2016-11-24 9:55 UTC (permalink / raw)
To: linux-arm-kernel
This patch series adds kdump support on arm64.
To load a crash-dump kernel to the systems, a series of patches to
kexec-tools[1] are also needed. Please use the latest one, v4 [2].
To examine vmcore (/proc/vmcore) on a crash-dump kernel, you can use
- crash utility (v7.1.6 or later) [3]
I validated this patchset on fast model.
The previous version, v27, was also:
Tested-by: Pratyush Anand <panand@redhat.com> (mustang and seattle)
Tested-by: James Morse <james.morse@arm.com> (Juno)
For your convenience, you can also find the patches:
https://git.linaro.org/people/takahiro.akashi/linux-aarch64.git arm64/kdump
https://git.linaro.org/people/takahiro.akashi/kexec-tools.git arm64/kdump
[1] https://git.kernel.org/pub/scm/utils/kernel/kexec/kexec-tools.git
[2] http://lists.infradead.org/pipermail/kexec/2016-November/017555.html
[3] https://github.com/crash-utility/crash.git
Changes for v28 (Nov 22, 2016)
o rebased to Linux-v4.9-rc6
o revamp patch #1 and merge memblock_cap_memory_range() with
memblock_mem_limit_remove_map()
Changes for v27 (Nov 1, 2016)
o rebased to Linux-v4.9-rc3
o revert v26 change, i.e. revive "linux,usable-memory-range" property
(patch #2/#3, updating patch #9)
o minor fixes per review comments (patch #3/#4/#6/#8)
o re-order patches and improve commit messages for readability
Changes for v26 (Sep 7, 2016):
o Use /reserved-memory instead of "linux,usable-memory-range" property
(dropping v25's patch#2 and #3, updating ex-patch#9.)
Changes for v25 (Aug 29, 2016):
o Rebase to Linux-4.8-rc4
o Use memremap() instead of ioremap_cache() [patch#5]
Changes for v24 (Aug 9, 2016):
o Rebase to Linux-4.8-rc1
o Update descriptions about newly added DT proerties
Changes for v23 (July 26, 2016):
o Move memblock_reserve() to a single place in reserve_crashkernel()
o Use cpu_park_loop() in ipi_cpu_crash_stop()
o Always enforce ARCH_LOW_ADDRESS_LIMIT to the memory range of crash kernel
o Re-implement fdt_enforce_memory_region() to remove non-reserve regions
(for ACPI) from usable memory at crash kernel
Changes for v22 (July 12, 2016):
o Export "crashkernel-base" and "crashkernel-size" via device-tree,
and add some descriptions about them in chosen.txt
o Rename "usable-memory" to "usable-memory-range" to avoid inconsistency
with powerpc's "usable-memory"
o Make cosmetic changes regarding "ifdef" usage
o Correct some wordings in kdump.txt
Changes for v21 (July 6, 2016):
o Remove kexec patches.
o Rebase to arm64's for-next/core (Linux-4.7-rc4 based).
o Clarify the description about kvm in kdump.txt.
See the following link [4] for older changes:
[4] http://lists.infradead.org/pipermail/linux-arm-kernel/2016-June/438780.html
AKASHI Takahiro (8):
arm64: kdump: reserve memory for crash dump kernel
memblock: add memblock_cap_memory_range()
arm64: limit memory regions based on DT property, usable-memory-range
arm64: kdump: implement machine_crash_shutdown()
arm64: kdump: add kdump support
arm64: kdump: add VMCOREINFO's for user-space coredump tools
arm64: kdump: enable kdump in the arm64 defconfig
arm64: kdump: update a kernel doc
James Morse (1):
Documentation: dt: chosen properties for arm64 kdump
Documentation/devicetree/bindings/chosen.txt | 45 ++++++
Documentation/kdump/kdump.txt | 16 ++-
arch/arm64/Kconfig | 11 ++
arch/arm64/configs/defconfig | 1 +
arch/arm64/include/asm/hardirq.h | 2 +-
arch/arm64/include/asm/kexec.h | 41 +++++-
arch/arm64/include/asm/smp.h | 2 +
arch/arm64/kernel/Makefile | 1 +
arch/arm64/kernel/crash_dump.c | 71 ++++++++++
arch/arm64/kernel/machine_kexec.c | 67 ++++++++-
arch/arm64/kernel/setup.c | 7 +-
arch/arm64/kernel/smp.c | 63 +++++++++
arch/arm64/mm/init.c | 202 +++++++++++++++++++++++++++
include/linux/memblock.h | 1 +
mm/memblock.c | 28 ++++
15 files changed, 551 insertions(+), 7 deletions(-)
create mode 100644 arch/arm64/kernel/crash_dump.c
--
2.9.0
AKASHI Takahiro (8):
memblock: add memblock_cap_memory_range()
arm64: limit memory regions based on DT property, usable-memory-range
arm64: kdump: reserve memory for crash dump kernel
arm64: kdump: implement machine_crash_shutdown()
arm64: kdump: add VMCOREINFO's for user-space tools
arm64: kdump: provide /proc/vmcore file
arm64: kdump: enable kdump in defconfig
Documentation: kdump: describe arm64 port
James Morse (1):
Documentation: dt: chosen properties for arm64 kdump
Documentation/devicetree/bindings/chosen.txt | 50 +++++++
Documentation/kdump/kdump.txt | 16 ++-
arch/arm64/Kconfig | 11 ++
arch/arm64/configs/defconfig | 1 +
arch/arm64/include/asm/hardirq.h | 2 +-
arch/arm64/include/asm/kexec.h | 42 +++++-
arch/arm64/include/asm/smp.h | 2 +
arch/arm64/kernel/Makefile | 1 +
arch/arm64/kernel/crash_dump.c | 71 ++++++++++
arch/arm64/kernel/machine_kexec.c | 67 ++++++++-
arch/arm64/kernel/setup.c | 7 +-
arch/arm64/kernel/smp.c | 63 +++++++++
arch/arm64/mm/init.c | 199 +++++++++++++++++++++++++++
include/linux/memblock.h | 1 +
mm/memblock.c | 44 ++++--
15 files changed, 555 insertions(+), 22 deletions(-)
create mode 100644 arch/arm64/kernel/crash_dump.c
--
2.10.0
^ permalink raw reply
* [PATCH 7/10] mmc: sdhci-xenon: Add support to PHYs of Marvell Xenon SDHC
From: Arnd Bergmann @ 2016-11-24 9:56 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <a05ffd140f4edc02fc3128db8445b2264cf38723.1477911954.git-series.gregory.clement@free-electrons.com>
On Monday, October 31, 2016 12:09:56 PM CET Gregory CLEMENT wrote:
> From: Ziji Hu <huziji@marvell.com>
>
> Marvell Xenon eMMC/SD/SDIO Host Controller contains PHY.
> Three types of PHYs are supported.
>
> Add support to multiple types of PHYs init and configuration.
> Add register definitions of PHYs.
>
> Signed-off-by: Hu Ziji <huziji@marvell.com>
> Signed-off-by: Gregory CLEMENT <gregory.clement@free-electrons.com>
>
Please explain in the changelog why this is not a generic
phy driver (or three of them).
Arnd
^ permalink raw reply
* [PATCH v28 1/9] memblock: add memblock_cap_memory_range()
From: AKASHI Takahiro @ 2016-11-24 9:57 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
Add memblock_cap_memory_range() which will remove all the memblock regions
except the memory range specified in the arguments. In addition, rework is
done on memblock_mem_limit_remove_map() to re-implement it using
memblock_cap_memory_range().
This function, like memblock_mem_limit_remove_map(), will not remove
memblocks with MEMMAP_NOMAP attribute as they may be mapped and accessed
later as "device memory."
See the commit a571d4eb55d8 ("mm/memblock.c: add new infrastructure to
address the mem limit issue").
This function is used, in a succeeding patch in the series of arm64 kdump
suuport, to limit the range of usable memory, or System RAM, on crash dump
kernel.
(Please note that "mem=" parameter is of little use for this purpose.)
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
Reviewed-by: Will Deacon <will.deacon@arm.com>
Cc: linux-mm at kvack.org
Cc: Andrew Morton <akpm@linux-foundation.org>
---
include/linux/memblock.h | 1 +
mm/memblock.c | 44 +++++++++++++++++++++++++++++---------------
2 files changed, 30 insertions(+), 15 deletions(-)
diff --git a/include/linux/memblock.h b/include/linux/memblock.h
index 5b759c9..fbfcacc 100644
--- a/include/linux/memblock.h
+++ b/include/linux/memblock.h
@@ -333,6 +333,7 @@ phys_addr_t memblock_mem_size(unsigned long limit_pfn);
phys_addr_t memblock_start_of_DRAM(void);
phys_addr_t memblock_end_of_DRAM(void);
void memblock_enforce_memory_limit(phys_addr_t memory_limit);
+void memblock_cap_memory_range(phys_addr_t base, phys_addr_t size);
void memblock_mem_limit_remove_map(phys_addr_t limit);
bool memblock_is_memory(phys_addr_t addr);
int memblock_is_map_memory(phys_addr_t addr);
diff --git a/mm/memblock.c b/mm/memblock.c
index 7608bc3..fea1688 100644
--- a/mm/memblock.c
+++ b/mm/memblock.c
@@ -1514,11 +1514,37 @@ void __init memblock_enforce_memory_limit(phys_addr_t limit)
(phys_addr_t)ULLONG_MAX);
}
+void __init memblock_cap_memory_range(phys_addr_t base, phys_addr_t size)
+{
+ int start_rgn, end_rgn;
+ int i, ret;
+
+ if (!size)
+ return;
+
+ ret = memblock_isolate_range(&memblock.memory, base, size,
+ &start_rgn, &end_rgn);
+ if (ret)
+ return;
+
+ /* remove all the MAP regions */
+ for (i = memblock.memory.cnt - 1; i >= end_rgn; i--)
+ if (!memblock_is_nomap(&memblock.memory.regions[i]))
+ memblock_remove_region(&memblock.memory, i);
+
+ for (i = start_rgn - 1; i >= 0; i--)
+ if (!memblock_is_nomap(&memblock.memory.regions[i]))
+ memblock_remove_region(&memblock.memory, i);
+
+ /* truncate the reserved regions */
+ memblock_remove_range(&memblock.reserved, 0, base);
+ memblock_remove_range(&memblock.reserved,
+ base + size, (phys_addr_t)ULLONG_MAX);
+}
+
void __init memblock_mem_limit_remove_map(phys_addr_t limit)
{
- struct memblock_type *type = &memblock.memory;
phys_addr_t max_addr;
- int i, ret, start_rgn, end_rgn;
if (!limit)
return;
@@ -1529,19 +1555,7 @@ void __init memblock_mem_limit_remove_map(phys_addr_t limit)
if (max_addr == (phys_addr_t)ULLONG_MAX)
return;
- ret = memblock_isolate_range(type, max_addr, (phys_addr_t)ULLONG_MAX,
- &start_rgn, &end_rgn);
- if (ret)
- return;
-
- /* remove all the MAP regions above the limit */
- for (i = end_rgn - 1; i >= start_rgn; i--) {
- if (!memblock_is_nomap(&type->regions[i]))
- memblock_remove_region(type, i);
- }
- /* truncate the reserved regions */
- memblock_remove_range(&memblock.reserved, max_addr,
- (phys_addr_t)ULLONG_MAX);
+ memblock_cap_memory_range(0, max_addr);
}
static int __init_memblock memblock_search(struct memblock_type *type, phys_addr_t addr)
--
2.10.0
^ permalink raw reply related
* [PATCH v28 2/9] arm64: limit memory regions based on DT property, usable-memory-range
From: AKASHI Takahiro @ 2016-11-24 9:58 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
Crash dump kernel utilizes only a subset of available memory as System RAM.
On arm64 kdump, This memory range is advertized to crash dump kernel via
a device-tree property under /chosen,
linux,usable-memory-range = <BASE SIZE>
Crash dump kernel reads this property at boot time and calls
memblock_cap_memory_range() to limit usable memory ranges which are
described as entries in UEFI memory map table or "memory" nodes in
a device tree blob.
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
Reviewed-by: Geoff Levand <geoff@infradead.org>
---
arch/arm64/mm/init.c | 35 +++++++++++++++++++++++++++++++++++
1 file changed, 35 insertions(+)
diff --git a/arch/arm64/mm/init.c b/arch/arm64/mm/init.c
index 212c4d1..65f1241 100644
--- a/arch/arm64/mm/init.c
+++ b/arch/arm64/mm/init.c
@@ -187,10 +187,45 @@ static int __init early_mem(char *p)
}
early_param("mem", early_mem);
+static int __init early_init_dt_scan_usablemem(unsigned long node,
+ const char *uname, int depth, void *data)
+{
+ struct memblock_region *usablemem = (struct memblock_region *)data;
+ const __be32 *reg;
+ int len;
+
+ usablemem->size = 0;
+
+ if (depth != 1 || strcmp(uname, "chosen") != 0)
+ return 0;
+
+ reg = of_get_flat_dt_prop(node, "linux,usable-memory-range", &len);
+ if (!reg || (len < (dt_root_addr_cells + dt_root_size_cells)))
+ return 1;
+
+ usablemem->base = dt_mem_next_cell(dt_root_addr_cells, ®);
+ usablemem->size = dt_mem_next_cell(dt_root_size_cells, ®);
+
+ return 1;
+}
+
+static void __init fdt_enforce_memory_region(void)
+{
+ struct memblock_region reg;
+
+ of_scan_flat_dt(early_init_dt_scan_usablemem, ®);
+
+ if (reg.size)
+ memblock_cap_memory_range(reg.base, reg.size);
+}
+
void __init arm64_memblock_init(void)
{
const s64 linear_region_size = -(s64)PAGE_OFFSET;
+ /* Handle linux,usable-memory-range property */
+ fdt_enforce_memory_region();
+
/*
* Ensure that the linear region takes up exactly half of the kernel
* virtual address space. This way, we can distinguish a linear address
--
2.10.0
^ permalink raw reply related
* [PATCH v28 3/9] arm64: kdump: reserve memory for crash dump kernel
From: AKASHI Takahiro @ 2016-11-24 9:58 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
"crashkernel=" kernel parameter specifies the size (and optionally
the start address) of the system ram used by crash dump kernel.
reserve_crashkernel() will allocate and reserve the memory at the startup
of primary kernel.
This memory range will be exported to userspace via:
- an entry named "Crash kernel" in /proc/iomem, and
- "linux,crashkernel-base" and "linux,crashkernel-size" under
/sys/firmware/devicetree/base/chosen
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
Signed-off-by: Mark Salter <msalter@redhat.com>
Signed-off-by: Pratyush Anand <panand@redhat.com>
Reviewed-by: James Morse <james.morse@arm.com>
---
arch/arm64/kernel/setup.c | 7 ++-
arch/arm64/mm/init.c | 110 ++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 116 insertions(+), 1 deletion(-)
diff --git a/arch/arm64/kernel/setup.c b/arch/arm64/kernel/setup.c
index f534f49..f012659 100644
--- a/arch/arm64/kernel/setup.c
+++ b/arch/arm64/kernel/setup.c
@@ -31,7 +31,6 @@
#include <linux/screen_info.h>
#include <linux/init.h>
#include <linux/kexec.h>
-#include <linux/crash_dump.h>
#include <linux/root_dev.h>
#include <linux/cpu.h>
#include <linux/interrupt.h>
@@ -225,6 +224,12 @@ static void __init request_standard_resources(void)
kernel_data.end <= res->end)
request_resource(res, &kernel_data);
}
+
+#ifdef CONFIG_KEXEC_CORE
+ /* User space tools will find "Crash kernel" region in /proc/iomem. */
+ if (crashk_res.end)
+ insert_resource(&iomem_resource, &crashk_res);
+#endif
}
u64 __cpu_logical_map[NR_CPUS] = { [0 ... NR_CPUS-1] = INVALID_HWID };
diff --git a/arch/arm64/mm/init.c b/arch/arm64/mm/init.c
index 65f1241..1d62bf7 100644
--- a/arch/arm64/mm/init.c
+++ b/arch/arm64/mm/init.c
@@ -30,12 +30,14 @@
#include <linux/gfp.h>
#include <linux/memblock.h>
#include <linux/sort.h>
+#include <linux/of.h>
#include <linux/of_fdt.h>
#include <linux/dma-mapping.h>
#include <linux/dma-contiguous.h>
#include <linux/efi.h>
#include <linux/swiotlb.h>
#include <linux/vmalloc.h>
+#include <linux/kexec.h>
#include <asm/boot.h>
#include <asm/fixmap.h>
@@ -76,6 +78,111 @@ static int __init early_initrd(char *p)
early_param("initrd", early_initrd);
#endif
+#ifdef CONFIG_KEXEC_CORE
+static unsigned long long crash_size, crash_base;
+static struct property crash_base_prop = {
+ .name = "linux,crashkernel-base",
+ .length = sizeof(u64),
+ .value = &crash_base
+};
+static struct property crash_size_prop = {
+ .name = "linux,crashkernel-size",
+ .length = sizeof(u64),
+ .value = &crash_size,
+};
+
+static int __init export_crashkernel(void)
+{
+ struct device_node *node;
+ int ret;
+
+ if (!crash_size)
+ return 0;
+
+ /* Add /chosen/linux,crashkernel-* properties */
+ node = of_find_node_by_path("/chosen");
+ if (!node)
+ return -ENOENT;
+
+ /*
+ * There might be existing crash kernel properties, but we can't
+ * be sure what's in them, so remove them.
+ */
+ of_remove_property(node, of_find_property(node,
+ "linux,crashkernel-base", NULL));
+ of_remove_property(node, of_find_property(node,
+ "linux,crashkernel-size", NULL));
+
+ ret = of_add_property(node, &crash_base_prop);
+ if (ret)
+ goto ret_err;
+
+ ret = of_add_property(node, &crash_size_prop);
+ if (ret)
+ goto ret_err;
+
+ return 0;
+
+ret_err:
+ pr_warn("Exporting crashkernel region to device tree failed\n");
+ return ret;
+}
+late_initcall(export_crashkernel);
+
+/*
+ * reserve_crashkernel() - reserves memory for crash kernel
+ *
+ * This function reserves memory area given in "crashkernel=" kernel command
+ * line parameter. The memory reserved is used by dump capture kernel when
+ * primary kernel is crashing.
+ */
+static void __init reserve_crashkernel(void)
+{
+ int ret;
+
+ ret = parse_crashkernel(boot_command_line, memblock_phys_mem_size(),
+ &crash_size, &crash_base);
+ /* no crashkernel= or invalid value specified */
+ if (ret || !crash_size)
+ return;
+
+ if (crash_base == 0) {
+ /* Current arm64 boot protocol requires 2MB alignment */
+ crash_base = memblock_find_in_range(0, ARCH_LOW_ADDRESS_LIMIT,
+ crash_size, SZ_2M);
+ if (crash_base == 0) {
+ pr_warn("Unable to allocate crashkernel (size:%llx)\n",
+ crash_size);
+ return;
+ }
+ } else {
+ /* User specifies base address explicitly. */
+ if (!memblock_is_region_memory(crash_base, crash_size) ||
+ memblock_is_region_reserved(crash_base, crash_size)) {
+ pr_warn("crashkernel has wrong address or size\n");
+ return;
+ }
+
+ if (!IS_ALIGNED(crash_base, SZ_2M)) {
+ pr_warn("crashkernel base address is not 2MB aligned\n");
+ return;
+ }
+ }
+ memblock_reserve(crash_base, crash_size);
+
+ pr_info("Reserving %lldMB of memory at %lldMB for crashkernel\n",
+ crash_size >> 20, crash_base >> 20);
+
+ crashk_res.start = crash_base;
+ crashk_res.end = crash_base + crash_size - 1;
+}
+#else
+static void __init reserve_crashkernel(void)
+{
+ ;
+}
+#endif /* CONFIG_KEXEC_CORE */
+
/*
* Return the maximum physical address for ZONE_DMA (DMA_BIT_MASK(32)). It
* currently assumes that for memory starting above 4G, 32-bit devices will
@@ -331,6 +438,9 @@ void __init arm64_memblock_init(void)
arm64_dma_phys_limit = max_zone_dma_phys();
else
arm64_dma_phys_limit = PHYS_MASK + 1;
+
+ reserve_crashkernel();
+
dma_contiguous_reserve(arm64_dma_phys_limit);
memblock_allow_resize();
--
2.10.0
^ permalink raw reply related
* [PATCH v28 4/9] arm64: kdump: implement machine_crash_shutdown()
From: AKASHI Takahiro @ 2016-11-24 9:58 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
Primary kernel calls machine_crash_shutdown() to shut down non-boot cpus
and save registers' status in per-cpu ELF notes before starting crash
dump kernel. See kernel_kexec().
Even if not all secondary cpus have shut down, we do kdump anyway.
As we don't have to make non-boot(crashed) cpus offline (to preserve
correct status of cpus at crash dump) before shutting down, this patch
also adds a variant of smp_send_stop().
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
Reviewed-by: James Morse <james.morse@arm.com>
---
arch/arm64/include/asm/hardirq.h | 2 +-
arch/arm64/include/asm/kexec.h | 42 +++++++++++++++++++++++++-
arch/arm64/include/asm/smp.h | 2 ++
arch/arm64/kernel/machine_kexec.c | 56 ++++++++++++++++++++++++++++++++--
arch/arm64/kernel/smp.c | 63 +++++++++++++++++++++++++++++++++++++++
5 files changed, 160 insertions(+), 5 deletions(-)
diff --git a/arch/arm64/include/asm/hardirq.h b/arch/arm64/include/asm/hardirq.h
index 8740297..1473fc2 100644
--- a/arch/arm64/include/asm/hardirq.h
+++ b/arch/arm64/include/asm/hardirq.h
@@ -20,7 +20,7 @@
#include <linux/threads.h>
#include <asm/irq.h>
-#define NR_IPI 6
+#define NR_IPI 7
typedef struct {
unsigned int __softirq_pending;
diff --git a/arch/arm64/include/asm/kexec.h b/arch/arm64/include/asm/kexec.h
index 04744dc..b5168e8 100644
--- a/arch/arm64/include/asm/kexec.h
+++ b/arch/arm64/include/asm/kexec.h
@@ -40,7 +40,47 @@
static inline void crash_setup_regs(struct pt_regs *newregs,
struct pt_regs *oldregs)
{
- /* Empty routine needed to avoid build errors. */
+ if (oldregs) {
+ memcpy(newregs, oldregs, sizeof(*newregs));
+ } else {
+ u64 tmp1, tmp2;
+
+ __asm__ __volatile__ (
+ "stp x0, x1, [%2, #16 * 0]\n"
+ "stp x2, x3, [%2, #16 * 1]\n"
+ "stp x4, x5, [%2, #16 * 2]\n"
+ "stp x6, x7, [%2, #16 * 3]\n"
+ "stp x8, x9, [%2, #16 * 4]\n"
+ "stp x10, x11, [%2, #16 * 5]\n"
+ "stp x12, x13, [%2, #16 * 6]\n"
+ "stp x14, x15, [%2, #16 * 7]\n"
+ "stp x16, x17, [%2, #16 * 8]\n"
+ "stp x18, x19, [%2, #16 * 9]\n"
+ "stp x20, x21, [%2, #16 * 10]\n"
+ "stp x22, x23, [%2, #16 * 11]\n"
+ "stp x24, x25, [%2, #16 * 12]\n"
+ "stp x26, x27, [%2, #16 * 13]\n"
+ "stp x28, x29, [%2, #16 * 14]\n"
+ "mov %0, sp\n"
+ "stp x30, %0, [%2, #16 * 15]\n"
+
+ "/* faked current PSTATE */\n"
+ "mrs %0, CurrentEL\n"
+ "mrs %1, SPSEL\n"
+ "orr %0, %0, %1\n"
+ "mrs %1, DAIF\n"
+ "orr %0, %0, %1\n"
+ "mrs %1, NZCV\n"
+ "orr %0, %0, %1\n"
+ /* pc */
+ "adr %1, 1f\n"
+ "1:\n"
+ "stp %1, %0, [%2, #16 * 16]\n"
+ : "+r" (tmp1), "+r" (tmp2)
+ : "r" (newregs)
+ : "memory"
+ );
+ }
}
#endif /* __ASSEMBLY__ */
diff --git a/arch/arm64/include/asm/smp.h b/arch/arm64/include/asm/smp.h
index 0226447..6b0f2c7 100644
--- a/arch/arm64/include/asm/smp.h
+++ b/arch/arm64/include/asm/smp.h
@@ -136,6 +136,8 @@ static inline void cpu_panic_kernel(void)
*/
bool cpus_are_stuck_in_kernel(void);
+extern void smp_send_crash_stop(void);
+
#endif /* ifndef __ASSEMBLY__ */
#endif /* ifndef __ASM_SMP_H */
diff --git a/arch/arm64/kernel/machine_kexec.c b/arch/arm64/kernel/machine_kexec.c
index bc96c8a..c60346d 100644
--- a/arch/arm64/kernel/machine_kexec.c
+++ b/arch/arm64/kernel/machine_kexec.c
@@ -9,6 +9,9 @@
* published by the Free Software Foundation.
*/
+#include <linux/interrupt.h>
+#include <linux/irq.h>
+#include <linux/kernel.h>
#include <linux/kexec.h>
#include <linux/smp.h>
@@ -22,6 +25,7 @@
extern const unsigned char arm64_relocate_new_kernel[];
extern const unsigned long arm64_relocate_new_kernel_size;
+static bool in_crash_kexec;
static unsigned long kimage_start;
/**
@@ -148,7 +152,8 @@ void machine_kexec(struct kimage *kimage)
/*
* New cpus may have become stuck_in_kernel after we loaded the image.
*/
- BUG_ON(cpus_are_stuck_in_kernel() || (num_online_cpus() > 1));
+ BUG_ON((cpus_are_stuck_in_kernel() || (num_online_cpus() > 1)) &&
+ !WARN_ON(in_crash_kexec));
reboot_code_buffer_phys = page_to_phys(kimage->control_code_page);
reboot_code_buffer = phys_to_virt(reboot_code_buffer_phys);
@@ -200,13 +205,58 @@ void machine_kexec(struct kimage *kimage)
* relocation is complete.
*/
- cpu_soft_restart(1, reboot_code_buffer_phys, kimage->head,
+ cpu_soft_restart(!in_crash_kexec, reboot_code_buffer_phys, kimage->head,
kimage_start, 0);
BUG(); /* Should never get here. */
}
+static void machine_kexec_mask_interrupts(void)
+{
+ unsigned int i;
+ struct irq_desc *desc;
+
+ for_each_irq_desc(i, desc) {
+ struct irq_chip *chip;
+ int ret;
+
+ chip = irq_desc_get_chip(desc);
+ if (!chip)
+ continue;
+
+ /*
+ * First try to remove the active state. If this
+ * fails, try to EOI the interrupt.
+ */
+ ret = irq_set_irqchip_state(i, IRQCHIP_STATE_ACTIVE, false);
+
+ if (ret && irqd_irq_inprogress(&desc->irq_data) &&
+ chip->irq_eoi)
+ chip->irq_eoi(&desc->irq_data);
+
+ if (chip->irq_mask)
+ chip->irq_mask(&desc->irq_data);
+
+ if (chip->irq_disable && !irqd_irq_disabled(&desc->irq_data))
+ chip->irq_disable(&desc->irq_data);
+ }
+}
+
+/**
+ * machine_crash_shutdown - shutdown non-crashing cpus and save registers
+ */
void machine_crash_shutdown(struct pt_regs *regs)
{
- /* Empty routine needed to avoid build errors. */
+ local_irq_disable();
+
+ in_crash_kexec = true;
+
+ /* shutdown non-crashing cpus */
+ smp_send_crash_stop();
+
+ /* for crashing cpu */
+ crash_save_cpu(regs, smp_processor_id());
+ machine_kexec_mask_interrupts();
+
+ pr_info("Starting crashdump kernel...\n");
}
diff --git a/arch/arm64/kernel/smp.c b/arch/arm64/kernel/smp.c
index 8507703..8f8fd3ad 100644
--- a/arch/arm64/kernel/smp.c
+++ b/arch/arm64/kernel/smp.c
@@ -37,6 +37,7 @@
#include <linux/completion.h>
#include <linux/of.h>
#include <linux/irq_work.h>
+#include <linux/kexec.h>
#include <asm/alternative.h>
#include <asm/atomic.h>
@@ -71,6 +72,7 @@ enum ipi_msg_type {
IPI_RESCHEDULE,
IPI_CALL_FUNC,
IPI_CPU_STOP,
+ IPI_CPU_CRASH_STOP,
IPI_TIMER,
IPI_IRQ_WORK,
IPI_WAKEUP
@@ -745,6 +747,7 @@ static const char *ipi_types[NR_IPI] __tracepoint_string = {
S(IPI_RESCHEDULE, "Rescheduling interrupts"),
S(IPI_CALL_FUNC, "Function call interrupts"),
S(IPI_CPU_STOP, "CPU stop interrupts"),
+ S(IPI_CPU_CRASH_STOP, "CPU stop (for crash dump) interrupts"),
S(IPI_TIMER, "Timer broadcast interrupts"),
S(IPI_IRQ_WORK, "IRQ work interrupts"),
S(IPI_WAKEUP, "CPU wake-up interrupts"),
@@ -819,6 +822,29 @@ static void ipi_cpu_stop(unsigned int cpu)
cpu_relax();
}
+#ifdef CONFIG_KEXEC_CORE
+static atomic_t waiting_for_crash_ipi;
+#endif
+
+static void ipi_cpu_crash_stop(unsigned int cpu, struct pt_regs *regs)
+{
+#ifdef CONFIG_KEXEC_CORE
+ crash_save_cpu(regs, cpu);
+
+ atomic_dec(&waiting_for_crash_ipi);
+
+ local_irq_disable();
+
+#ifdef CONFIG_HOTPLUG_CPU
+ if (cpu_ops[cpu]->cpu_die)
+ cpu_ops[cpu]->cpu_die(cpu);
+#endif
+
+ /* just in case */
+ cpu_park_loop();
+#endif
+}
+
/*
* Main handler for inter-processor interrupts
*/
@@ -849,6 +875,15 @@ void handle_IPI(int ipinr, struct pt_regs *regs)
irq_exit();
break;
+ case IPI_CPU_CRASH_STOP:
+ if (IS_ENABLED(CONFIG_KEXEC_CORE)) {
+ irq_enter();
+ ipi_cpu_crash_stop(cpu, regs);
+
+ unreachable();
+ }
+ break;
+
#ifdef CONFIG_GENERIC_CLOCKEVENTS_BROADCAST
case IPI_TIMER:
irq_enter();
@@ -921,6 +956,34 @@ void smp_send_stop(void)
cpumask_pr_args(cpu_online_mask));
}
+#ifdef CONFIG_KEXEC_CORE
+void smp_send_crash_stop(void)
+{
+ cpumask_t mask;
+ unsigned long timeout;
+
+ if (num_online_cpus() == 1)
+ return;
+
+ cpumask_copy(&mask, cpu_online_mask);
+ cpumask_clear_cpu(smp_processor_id(), &mask);
+
+ atomic_set(&waiting_for_crash_ipi, num_online_cpus() - 1);
+
+ pr_crit("SMP: stopping secondary CPUs\n");
+ smp_cross_call(&mask, IPI_CPU_CRASH_STOP);
+
+ /* Wait up to one second for other CPUs to stop */
+ timeout = USEC_PER_SEC;
+ while ((atomic_read(&waiting_for_crash_ipi) > 0) && timeout--)
+ udelay(1);
+
+ if (atomic_read(&waiting_for_crash_ipi) > 0)
+ pr_warning("SMP: failed to stop secondary CPUs %*pbl\n",
+ cpumask_pr_args(cpu_online_mask));
+}
+#endif
+
/*
* not supported here
*/
--
2.10.0
^ permalink raw reply related
* [PATCH v28 5/9] arm64: kdump: add VMCOREINFO's for user-space tools
From: AKASHI Takahiro @ 2016-11-24 9:58 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
In addition to common VMCOREINFO's defined in
crash_save_vmcoreinfo_init(), we need to know, for crash utility,
- kimage_voffset
- PHYS_OFFSET
to examine the contents of a dump file (/proc/vmcore) correctly
due to the introduction of KASLR (CONFIG_RANDOMIZE_BASE) in v4.6.
- VA_BITS
is also required for makedumpfile command.
arch_crash_save_vmcoreinfo() appends them to the dump file.
More VMCOREINFO's may be added later.
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
Reviewed-by: James Morse <james.morse@arm.com>
---
arch/arm64/kernel/machine_kexec.c | 11 +++++++++++
1 file changed, 11 insertions(+)
diff --git a/arch/arm64/kernel/machine_kexec.c b/arch/arm64/kernel/machine_kexec.c
index c60346d..994fe0b 100644
--- a/arch/arm64/kernel/machine_kexec.c
+++ b/arch/arm64/kernel/machine_kexec.c
@@ -17,6 +17,7 @@
#include <asm/cacheflush.h>
#include <asm/cpu_ops.h>
+#include <asm/memory.h>
#include <asm/mmu_context.h>
#include "cpu-reset.h"
@@ -260,3 +261,13 @@ void machine_crash_shutdown(struct pt_regs *regs)
pr_info("Starting crashdump kernel...\n");
}
+
+void arch_crash_save_vmcoreinfo(void)
+{
+ VMCOREINFO_NUMBER(VA_BITS);
+ /* Please note VMCOREINFO_NUMBER() uses "%d", not "%x" */
+ vmcoreinfo_append_str("NUMBER(kimage_voffset)=0x%llx\n",
+ kimage_voffset);
+ vmcoreinfo_append_str("NUMBER(PHYS_OFFSET)=0x%llx\n",
+ PHYS_OFFSET);
+}
--
2.10.0
^ permalink raw reply related
* [PATCH v28 6/9] arm64: kdump: provide /proc/vmcore file
From: AKASHI Takahiro @ 2016-11-24 9:58 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
Add arch-specific functions to provide a dump file, /proc/vmcore.
This file is in ELF format and its ELF header needs to be prepared by
userspace tools, like kexec-tools, in adance. The primary kernel is
responsible to allocate the region with reserve_elfcorehdr() at boot time
and advertize its location to crash dump kernel via a new device-tree
property, "linux,elfcorehdr".
Then crash dump kernel will access the primary kernel's memory with
copy_oldmem_page(), which feeds the data page-by-page by ioremap'ing it
since it does not reside in linear mapping on crash dump kernel.
We also need our own elfcorehdr_read() here since the header is placed
within crash dump kernel's usable memory.
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
Reviewed-by: James Morse <james.morse@arm.com>
---
arch/arm64/Kconfig | 11 +++++++
arch/arm64/kernel/Makefile | 1 +
arch/arm64/kernel/crash_dump.c | 71 ++++++++++++++++++++++++++++++++++++++++++
arch/arm64/mm/init.c | 54 ++++++++++++++++++++++++++++++++
4 files changed, 137 insertions(+)
create mode 100644 arch/arm64/kernel/crash_dump.c
diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig
index 969ef88..399f84a 100644
--- a/arch/arm64/Kconfig
+++ b/arch/arm64/Kconfig
@@ -688,6 +688,17 @@ config KEXEC
but it is independent of the system firmware. And like a reboot
you can start any kernel with it, not just Linux.
+config CRASH_DUMP
+ bool "Build kdump crash kernel"
+ help
+ Generate crash dump after being started by kexec. This should
+ be normally only set in special crash dump kernels which are
+ loaded in the main kernel with kexec-tools into a specially
+ reserved region and then later executed after a crash by
+ kdump/kexec.
+
+ For more details see Documentation/kdump/kdump.txt
+
config XEN_DOM0
def_bool y
depends on XEN
diff --git a/arch/arm64/kernel/Makefile b/arch/arm64/kernel/Makefile
index 7d66bba..6a7384e 100644
--- a/arch/arm64/kernel/Makefile
+++ b/arch/arm64/kernel/Makefile
@@ -50,6 +50,7 @@ arm64-obj-$(CONFIG_RANDOMIZE_BASE) += kaslr.o
arm64-obj-$(CONFIG_HIBERNATION) += hibernate.o hibernate-asm.o
arm64-obj-$(CONFIG_KEXEC) += machine_kexec.o relocate_kernel.o \
cpu-reset.o
+arm64-obj-$(CONFIG_CRASH_DUMP) += crash_dump.o
obj-y += $(arm64-obj-y) vdso/ probes/
obj-m += $(arm64-obj-m)
diff --git a/arch/arm64/kernel/crash_dump.c b/arch/arm64/kernel/crash_dump.c
new file mode 100644
index 0000000..c3d5a21
--- /dev/null
+++ b/arch/arm64/kernel/crash_dump.c
@@ -0,0 +1,71 @@
+/*
+ * Routines for doing kexec-based kdump
+ *
+ * Copyright (C) 2014 Linaro Limited
+ * Author: AKASHI Takahiro <takahiro.akashi@linaro.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#include <linux/crash_dump.h>
+#include <linux/errno.h>
+#include <linux/io.h>
+#include <linux/memblock.h>
+#include <linux/uaccess.h>
+#include <asm/memory.h>
+
+/**
+ * copy_oldmem_page() - copy one page from old kernel memory
+ * @pfn: page frame number to be copied
+ * @buf: buffer where the copied page is placed
+ * @csize: number of bytes to copy
+ * @offset: offset in bytes into the page
+ * @userbuf: if set, @buf is in a user address space
+ *
+ * This function copies one page from old kernel memory into buffer pointed by
+ * @buf. If @buf is in userspace, set @userbuf to %1. Returns number of bytes
+ * copied or negative error in case of failure.
+ */
+ssize_t copy_oldmem_page(unsigned long pfn, char *buf,
+ size_t csize, unsigned long offset,
+ int userbuf)
+{
+ void *vaddr;
+
+ if (!csize)
+ return 0;
+
+ vaddr = memremap(__pfn_to_phys(pfn), PAGE_SIZE, MEMREMAP_WB);
+ if (!vaddr)
+ return -ENOMEM;
+
+ if (userbuf) {
+ if (copy_to_user((char __user *)buf, vaddr + offset, csize)) {
+ memunmap(vaddr);
+ return -EFAULT;
+ }
+ } else {
+ memcpy(buf, vaddr + offset, csize);
+ }
+
+ memunmap(vaddr);
+
+ return csize;
+}
+
+/**
+ * elfcorehdr_read - read from ELF core header
+ * @buf: buffer where the data is placed
+ * @csize: number of bytes to read
+ * @ppos: address in the memory
+ *
+ * This function reads @count bytes from elf core header which exists
+ * on crash dump kernel's memory.
+ */
+ssize_t elfcorehdr_read(char *buf, size_t count, u64 *ppos)
+{
+ memcpy(buf, phys_to_virt((phys_addr_t)*ppos), count);
+ return count;
+}
diff --git a/arch/arm64/mm/init.c b/arch/arm64/mm/init.c
index 1d62bf7..ef8adfd 100644
--- a/arch/arm64/mm/init.c
+++ b/arch/arm64/mm/init.c
@@ -38,6 +38,7 @@
#include <linux/swiotlb.h>
#include <linux/vmalloc.h>
#include <linux/kexec.h>
+#include <linux/crash_dump.h>
#include <asm/boot.h>
#include <asm/fixmap.h>
@@ -183,6 +184,57 @@ static void __init reserve_crashkernel(void)
}
#endif /* CONFIG_KEXEC_CORE */
+#ifdef CONFIG_CRASH_DUMP
+static int __init early_init_dt_scan_elfcorehdr(unsigned long node,
+ const char *uname, int depth, void *data)
+{
+ const __be32 *reg;
+ int len;
+
+ if (depth != 1 || strcmp(uname, "chosen") != 0)
+ return 0;
+
+ reg = of_get_flat_dt_prop(node, "linux,elfcorehdr", &len);
+ if (!reg || (len < (dt_root_addr_cells + dt_root_size_cells)))
+ return 1;
+
+ elfcorehdr_addr = dt_mem_next_cell(dt_root_addr_cells, ®);
+ elfcorehdr_size = dt_mem_next_cell(dt_root_size_cells, ®);
+
+ return 1;
+}
+
+/*
+ * reserve_elfcorehdr() - reserves memory for elf core header
+ *
+ * This function reserves elf core header given in "elfcorehdr=" kernel
+ * command line parameter. This region contains all the information about
+ * primary kernel's core image and is used by a dump capture kernel to
+ * access the system memory on primary kernel.
+ */
+static void __init reserve_elfcorehdr(void)
+{
+ of_scan_flat_dt(early_init_dt_scan_elfcorehdr, NULL);
+
+ if (!elfcorehdr_size)
+ return;
+
+ if (memblock_is_region_reserved(elfcorehdr_addr, elfcorehdr_size)) {
+ pr_warn("elfcorehdr is overlapped\n");
+ return;
+ }
+
+ memblock_reserve(elfcorehdr_addr, elfcorehdr_size);
+
+ pr_info("Reserving %lldKB of memory@0x%llx for elfcorehdr\n",
+ elfcorehdr_size >> 10, elfcorehdr_addr);
+}
+#else
+static void __init reserve_elfcorehdr(void)
+{
+ ;
+}
+#endif /* CONFIG_CRASH_DUMP */
/*
* Return the maximum physical address for ZONE_DMA (DMA_BIT_MASK(32)). It
* currently assumes that for memory starting above 4G, 32-bit devices will
@@ -441,6 +493,8 @@ void __init arm64_memblock_init(void)
reserve_crashkernel();
+ reserve_elfcorehdr();
+
dma_contiguous_reserve(arm64_dma_phys_limit);
memblock_allow_resize();
--
2.10.0
^ permalink raw reply related
* [PATCH v28 7/9] arm64: kdump: enable kdump in defconfig
From: AKASHI Takahiro @ 2016-11-24 9:58 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161124095523.6972-1-takahiro.akashi@linaro.org>
Kdump is enabled by default as kexec is.
Signed-off-by: AKASHI Takahiro <takahiro.akashi@linaro.org>
---
arch/arm64/configs/defconfig | 1 +
1 file changed, 1 insertion(+)
diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig
index dab2cb0..24922c9 100644
--- a/arch/arm64/configs/defconfig
+++ b/arch/arm64/configs/defconfig
@@ -79,6 +79,7 @@ CONFIG_CMA=y
CONFIG_SECCOMP=y
CONFIG_XEN=y
CONFIG_KEXEC=y
+CONFIG_CRASH_DUMP=y
# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
CONFIG_COMPAT=y
CONFIG_CPU_IDLE=y
--
2.10.0
^ 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