Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v9 07/11] arm64: kexec_file: add crash dump support
From: AKASHI Takahiro @ 2018-05-18  9:58 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <3d70c7d1-4985-a427-ecc6-a7edc84edfff@arm.com>

On Wed, May 16, 2018 at 09:34:41AM +0100, James Morse wrote:
> Hi Akashi,
> 
> On 15/05/18 18:11, James Morse wrote:
> > On 25/04/18 07:26, AKASHI Takahiro wrote:
> >> Enabling crash dump (kdump) includes
> >> * prepare contents of ELF header of a core dump file, /proc/vmcore,
> >>   using crash_prepare_elf64_headers(), and
> >> * add two device tree properties, "linux,usable-memory-range" and
> >>   "linux,elfcorehdr", which represent repsectively a memory range
> >>   to be used by crash dump kernel and the header's location
> 
> >> diff --git a/arch/arm64/kernel/machine_kexec_file.c b/arch/arm64/kernel/machine_kexec_file.c
> >> index 37c0a9dc2e47..ec674f4d267c 100644
> >> --- a/arch/arm64/kernel/machine_kexec_file.c
> >> +++ b/arch/arm64/kernel/machine_kexec_file.c
> >> @@ -76,6 +81,78 @@ int arch_kexec_walk_mem(struct kexec_buf *kbuf,
> 
> >> +static void fill_property(void *buf, u64 val64, int cells)
> >> +{
> >> +	u32 val32;
> >> +
> >> +	if (cells == 1) {
> >> +		val32 = cpu_to_fdt32((u32)val64);
> >> +		memcpy(buf, &val32, sizeof(val32));
> >> +	} else {
> > 
> >> +		memset(buf, 0, cells * sizeof(u32) - sizeof(u64));
> >> +		buf += cells * sizeof(u32) - sizeof(u64);
> > 
> > Is this trying to clear the 'top' cells and shuffle the pointer to point at the
> > 'bottom' 2? I'm pretty sure this isn't endian safe.
> 
> It came to me at 2am: this only works on big-endian, which is exactly what you
> want as that is the DT format.

Oops, I was almost tricked as I haven't tested kexec on BE
for a long time :)

Thanks,
-Takahiro AKASHI

> 
> > Do we really expect a system to have #address-cells > 2?
> 
> 
> Thanks,
> 
> James

^ permalink raw reply

* [PATCH 17/27] dt-bindings: ap806: add the thermal node in the syscon file
From: Miquel Raynal @ 2018-05-18  9:56 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180427210722.obyujepjvqc5hwcd@rob-hp-laptop>

Hi Rob,

Thanks for reviewing, one question below.

On Fri, 27 Apr 2018 16:07:22 -0500, Rob Herring <robh@kernel.org> wrote:

> On Sat, Apr 21, 2018 at 05:12:45PM +0200, Miquel Raynal wrote:
> > Explain the thermal bindings now that the thermal IP is described being
> > inside of a system controller. Add a reference to the thermal-zone node.
> > 
> > Signed-off-by: Miquel Raynal <miquel.raynal@bootlin.com>
> > ---
> >  .../arm/marvell/ap806-system-controller.txt        | 43 ++++++++++++++++++++++
> >  1 file changed, 43 insertions(+)
> > 
> > diff --git a/Documentation/devicetree/bindings/arm/marvell/ap806-system-controller.txt b/Documentation/devicetree/bindings/arm/marvell/ap806-system-controller.txt
> > index a856eb9a4e05..c95f3ac5c728 100644
> > --- a/Documentation/devicetree/bindings/arm/marvell/ap806-system-controller.txt
> > +++ b/Documentation/devicetree/bindings/arm/marvell/ap806-system-controller.txt
> > @@ -11,6 +11,9 @@ For the top level node:
> >   - compatible: must be: "syscon", "simple-mfd";
> >   - reg: register area of the AP806 system controller
> >  
> > +SYSTEM CONTROLLER 0
> > +===================
> > +
> >  Clocks:
> >  -------
> >  
> > @@ -98,3 +101,43 @@ ap_syscon: system-controller at 6f4000 {
> >  		gpio-ranges = <&ap_pinctrl 0 0 19>;
> >  	};
> >  };
> > +
> > +SYSTEM CONTROLLER 1
> > +===================
> > +
> > +Thermal:
> > +--------
> > +
> > +For common binding part and usage, refer to
> > +Documentation/devicetree/bindings/thermal/thermal.txt
> > +
> > +The thermal IP can probe the temperature all around the processor. It
> > +may feature several channels, each of them wired to one sensor.
> > +
> > +It is possible to setup an overheat interrupt by giving at least one
> > +critical point to any subnode of the thermal-zone node.
> > +
> > +Required properties:
> > +- compatible: "marvell,armada-ap806-thermal"
> > +
> > +Optional properties:
> > +- interrupt-parent/interrupts: overheat interrupt handle. Should point to
> > +  line 18 of the SEI irqchip.
> > +  See interrupt-controller/interrupts.txt
> > +- #thermal-sensor-cells: shall be <1> when thermal-zones subnodes refer
> > +  to this IP and represents the channel ID. There is one sensor per
> > +  channel. O refers to the thermal IP internal channel, while positive
> > +  IDs refer to each CPU.
> > +
> > +Example:
> > +ap_syscon1: system-controller at 6f8000 {
> > +	compatible = "syscon", "simple-mfd";
> > +	reg = <0x6f8000 0x1000>;
> > +
> > +	ap_thermal: ap-thermal {
> > +		compatible = "marvell,armada-ap806-thermal";  
> 
> Is there a register range associated with the thermal functions?

Indeed there is a small one (three registers) but we also need to access
some registers out of this area (so called the 'DFX' area, in this
syscon, to route correctly the interrupt) and I fear we'll need to
access others in the future. I choose to declare a syscon because this
area mixes a lot of misc registers.

So do you think I should declare these 3 registers area in a reg
property? Or keep the way I retrieved the offsets in the syscon:
defining offsets in the code?

> 
> > +		interrupt-parent = <&sei>;
> > +		interrupts = <18>;
> > +		#thermal-sensor-cells = <1>;
> > +	};
> > +};
> > -- 
> > 2.14.1
> >   

Thanks,
Miqu?l

-- 
Miquel Raynal, Bootlin (formerly Free Electrons)
Embedded Linux and Kernel engineering
https://bootlin.com

^ permalink raw reply

* [PATCH v9 07/11] arm64: kexec_file: add crash dump support
From: AKASHI Takahiro @ 2018-05-18  9:50 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <512cde7d-d84b-3623-cb09-a2d78acc11dc@arm.com>

On Wed, May 16, 2018 at 11:06:02AM +0100, James Morse wrote:
> Hi Akashi,
> 
> On 15/05/18 18:11, James Morse wrote:
> > On 25/04/18 07:26, AKASHI Takahiro wrote:
> >> Enabling crash dump (kdump) includes
> >> * prepare contents of ELF header of a core dump file, /proc/vmcore,
> >>   using crash_prepare_elf64_headers(), and
> >> * add two device tree properties, "linux,usable-memory-range" and
> >>   "linux,elfcorehdr", which represent repsectively a memory range
> >>   to be used by crash dump kernel and the header's location
> 
> >> diff --git a/arch/arm64/kernel/machine_kexec_file.c b/arch/arm64/kernel/machine_kexec_file.c
> >> index 37c0a9dc2e47..ec674f4d267c 100644
> >> --- a/arch/arm64/kernel/machine_kexec_file.c
> >> +++ b/arch/arm64/kernel/machine_kexec_file.c
> 
> >> +static struct crash_mem *get_crash_memory_ranges(void)
> >> +{
> >> +	unsigned int nr_ranges;
> >> +	struct crash_mem *cmem;
> >> +
> >> +	nr_ranges = 1; /* for exclusion of crashkernel region */
> >> +	walk_system_ram_res(0, -1, &nr_ranges, get_nr_ranges_callback);
> >> +
> >> +	cmem = vmalloc(sizeof(struct crash_mem) +
> >> +			sizeof(struct crash_mem_range) * nr_ranges);
> >> +	if (!cmem)
> >> +		return NULL;
> >> +
> >> +	cmem->max_nr_ranges = nr_ranges;
> >> +	cmem->nr_ranges = 0;
> >> +	walk_system_ram_res(0, -1, cmem, add_mem_range_callback);
> >> +
> >> +	/* Exclude crashkernel region */
> >> +	if (crash_exclude_mem_range(cmem, crashk_res.start, crashk_res.end)) {
> >> +		vfree(cmem);
> >> +		return NULL;
> >> +	}
> >> +
> >> +	return cmem;
> >> +}
> > 
> > Could this function be included in prepare_elf_headers() so that the alloc() and
> > free() occur together.
> > 
> > 
> >> +static int prepare_elf_headers(void **addr, unsigned long *sz)
> >> +{
> >> +	struct crash_mem *cmem;
> >> +	int ret = 0;
> >> +
> >> +	cmem = get_crash_memory_ranges();
> >> +	if (!cmem)
> >> +		return -ENOMEM;
> >> +
> >> +	ret =  crash_prepare_elf64_headers(cmem, true, addr, sz);
> >> +
> >> +	vfree(cmem);
> > 
> >> +	return ret;
> >> +}
> > 
> > All this is moving memory-range information from core-code's
> > walk_system_ram_res() into core-code's struct crash_mem, and excluding
> > crashk_res, which again is accessible to the core code.
> > 
> > It looks like this is duplicated in arch/x86 and arch/arm64 because arm64
> > doesn't have a second 'crashk_low_res' region, and always wants elf64, instead
> > of when IS_ENABLED(CONFIG_X86_64).
> 
> Thinking about it some more: don't we want to walk memblock here, not
> walk_system_ram_res()? What we want is a list of not-nomap regions that the
> kernel may have been using, to form part of vmcore.
> walk_system_ram_res() is becoming a murkier list of maybe-nomap, maybe-reserved.
> 
> I think we should walk the same list here as we do in patch 4.

For consistency, yes.
I missed that.

-Takahiro AKASHI

> 
> 
> Thanks,
> 
> James

^ permalink raw reply

* [PATCH 3/3] arm64: dts: renesas: r8a7795: add ccree binding
From: Simon Horman @ 2018-05-18  9:50 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <CAOtvUMcnrPnkx35Sgru+3EUxYn+FY9FmDSYSNnZEaVUODHA7+w@mail.gmail.com>

On Thu, May 17, 2018 at 04:12:23PM +0300, Gilad Ben-Yossef wrote:
> On Thu, May 17, 2018 at 12:04 PM, Simon Horman <horms@verge.net.au> wrote:
> > On Thu, May 17, 2018 at 11:01:57AM +0300, Gilad Ben-Yossef wrote:
> >> On Wed, May 16, 2018 at 10:43 AM, Simon Horman <horms@verge.net.au> wrote:
> >> > On Tue, May 15, 2018 at 04:50:44PM +0200, Geert Uytterhoeven wrote:
> >> >> Hi Gilad,
> >> >>
> >> >> On Tue, May 15, 2018 at 2:29 PM, Gilad Ben-Yossef <gilad@benyossef.com> wrote:
> >> >> > Add bindings for CryptoCell instance in the SoC.
> >> >> >
> >> >> > Signed-off-by: Gilad Ben-Yossef <gilad@benyossef.com>
> >> >>
> >> >> Thanks for your patch!
> >> >>
> >> >> > --- a/arch/arm64/boot/dts/renesas/r8a7795.dtsi
> >> >> > +++ b/arch/arm64/boot/dts/renesas/r8a7795.dtsi
> >> >> > @@ -528,6 +528,14 @@
> >> >> >                         status = "disabled";
> >> >> >                 };
> >> >> >
> >> >> > +               arm_cc630p: crypto at e6601000 {
> >> >> > +                       compatible = "arm,cryptocell-630p-ree";
> >> >> > +                       interrupts = <GIC_SPI 71 IRQ_TYPE_LEVEL_HIGH>;
> >> >> > +                       #interrupt-cells = <2>;
> >> >>
> >> >> I believe the #interrupt-cells property is not needed.
> >> >>
> >> >> > +                       reg = <0x0 0xe6601000 0 0x1000>;
> >> >> > +                       clocks = <&cpg CPG_MOD 229>;
> >> >> > +               };
> >> >>
> >> >> The rest looks good, but I cannot verify the register block.
> >> >>
> >> >> > +
> >> >> >                 i2c3: i2c at e66d0000 {
> >> >> >                         #address-cells = <1>;
> >> >> >                         #size-cells = <0>;
> >> >
> >> > Thanks, I have applied this after dropping the #interrupt-cells property.
> >>
> >> Thanks you!
> >>
> >> Alas, it will not work without the clk patch (the previous one in the
> >> series) so they need to be
> >> taken or dropped together.
> >
> > I think its fine if it does not yet work.
> > But not if its causes things that previously worked to stop working.
> 
> Based on the further discussion with Geert my recommendation is to
> drop my patch for now,
> take Geert CR clock  patch and I will follow up next week with a v2
> that fixes the clock
> handing as discussed with Geert.

Thanks, I will drop the patch.

^ permalink raw reply

* [PATCH 00/27] Add multi-channel and overheat IRQ support to Armada thermal driver
From: Miquel Raynal @ 2018-05-18  9:49 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <871seb33xu.fsf@bootlin.com>

Hi Zhang, Eduardo & Gregory,

On Wed, 16 May 2018 19:28:45 +0200, Gregory CLEMENT
<gregory.clement@bootlin.com> wrote:

> Hi Miquel,
>  
>  On sam., avril 21 2018, Miquel Raynal <miquel.raynal@bootlin.com> wrote:
> 
> > The only capability of the Armada thermal driver is currently just to
> > read one sensor (the default one) per AP and one per CP.
> >
> > Actually, there is one sensor per core in the AP806 plus one sensor in
> > the thermal IP itself. The CP110 just features one thermal sensor in its
> > own thermal IP.
> >
> > Also, there is no need for the thermal core to poll the temperature of
> > each sensor by software as this IP (at least for AP806 and CP110
> > compatibles) features an hardware overheat interrupt.
> >
> > This series first improves the readability of this driver, then adds
> > support for multi-channel thermal IPs, and finally adds support for the
> > hardware overheat interrupt. The bindings and the device-trees are
> > updated accordingly.
> >
> > Please note that the thermal IP raises SEI interrupts, from which the
> > support as just been contributed and not merged yet. Applying the last
> > DT patches referring to the 'sei' and 'icu_sei' nodes will require this
> > feature [1] to have been accepted first.
> >
> > [1] http://lists.infradead.org/pipermail/linux-arm-kernel/2018-April/572852.html
> >
> > Thank you,
> > Miqu?l
> >
> >
> > Miquel Raynal (27):
> >   thermal: armada: add a function that sanitizes the thermal zone name
> >   thermal: armada: remove useless register accesses
> >   thermal: armada: remove misleading comments
> >   thermal: armada: rename the initialization routine
> >   thermal: armada: dissociate a380 and cp110 ->init() hooks
> >   thermal: armada: average over samples to avoid glitches
> >   thermal: armada: convert driver to syscon register accesses
> >   thermal: armada: use the resource managed registration helper
> >     alternative
> >   thermal: armada: add multi-channel sensors support
> >   thermal: armada: remove sensors validity from the IP initialization
> >   thermal: armada: move validity check out of the read function
> >   thermal: armada: get rid of the ->is_valid() pointer
> >   thermal: armada: add overheat interrupt support
> >   dt-bindings: cp110: rename cp110 syscon file
> >   dt-bindings: ap806: prepare the syscon file to list other syscons
> >     nodes
> >   dt-bindings: cp110: prepare the syscon file to list other syscons
> >     nodes
> >   dt-bindings: ap806: add the thermal node in the syscon file
> >   dt-bindings: cp110: update documentation since DT de-duplication
> >   dt-bindings: cp110: add the thermal node in the syscon file
> >   dt-bindings: thermal: armada: add reference to new bindings
> >   arm64: dts: marvell: rename ap806 syscon node
> >   arm64: dts: marvell: move AP806/CP110 thermal nodes into a new syscon
> >   arm64: dts: marvell: add thermal-zone node in ap806 DTSI file
> >   arm64: dts: marvell: add macro to make distinction between node names
> >   arm64: dts: marvell: add thermal-zone node in cp110 DTSI file
> >   arm64: dts: marvell: add interrupt support to ap806 thermal node
> >   arm64: dts: marvell: add interrupt support to cp110 thermal node
> >
> >  .../arm/marvell/ap806-system-controller.txt        |  55 +-
> >  ...controller0.txt => cp110-system-controller.txt} |  66 +-
> >  .../devicetree/bindings/thermal/armada-thermal.txt |   5 +
> >  arch/arm64/boot/dts/marvell/armada-ap806.dtsi      |  85 +-
> >  arch/arm64/boot/dts/marvell/armada-common.dtsi     |   1 +
> >  arch/arm64/boot/dts/marvell/armada-cp110.dtsi      |  45 +-
> >  drivers/thermal/armada_thermal.c                   | 875 ++++++++++++++++++---
> >  7 files changed, 976 insertions(+), 156 deletions(-)
> >  rename Documentation/devicetree/bindings/arm/marvell/{cp110-system-controller0.txt => cp110-system-controller.txt} (83%)  
> 
> What is the status of this series?
> I am especially interested in the dt part.
> Do you expect sending a new series modifying them?

I have not received any feedback yet on the thermal part, bindings have
been partially acked by Rob (one request, I will probably add a reg
property in the AP node) so please do not take the DTS changes of
this iteration.

Zhang, Eduardo, could you please share the status of this series?

Thanks,
Miqu?l

^ permalink raw reply

* [PATCH] arm: bcm2835: Add the PMU to the devicetree.
From: Marc Zyngier @ 2018-05-18  9:49 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1863838560.56771.1526636258081@email.1und1.de>

On 18/05/18 10:37, Stefan Wahren wrote:
> Hi Marc,
> 
>> Marc Zyngier <marc.zyngier@arm.com> hat am 18. Mai 2018 um 10:07 geschrieben:
>>
>> I have a pretty simple series[1] which I used to profile 32bit guests on
>> an arm64 KVM host. Nobody really cared about it because running a 32bit
>> kernel on 64bit HW is a bit odd, to say the least, and I'm probably the
>> only one actually running 32bit VMs.
>>
>>> FWIW, Broadcom STB chips, even when 64-bit capable or often used with an
>>> 32-bit ARM kernel, so having the ARMv8 PMUs work under a 32-bit ARM
>>> kernel would be great. The downstream solution we have sued thus far is
>>> to find the closest compatible string to represent those, which is not
>>> great...
>> Ah, so you're *really* doing that? I'm not going to ask why, I'm scared
>> of the answer... ;-)
>>
>> Anyway, I can repost that series if that will prevent people from having
>> that kind of silly hacks.
> 
> yes please. But there is a minor nit: some patches introduce new files without SPDX tags.
I'm shocked! ;-)

	M.
-- 
Jazz is not dead. It just smells funny...

^ permalink raw reply

* [PATCH]irqchip/irq-gic-v3:Avoid a waste of LPI resource
From: Zhang, Lei @ 2018-05-18  9:49 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <8898674D84E3B24BA3A2D289B872026A69F0ACA3@G01JPEXMBKW03>

Hi Marc

> -----Original Message-----
> From: linux-arm-kernel
> [mailto:linux-arm-kernel-bounces at lists.infradead.org] On Behalf Of Zhang,
> Lei
> Sent: Saturday, May 12, 2018 10:48 AM
> To: 'Marc Zyngier'; linux-arm-kernel at lists.infradead.org
> Subject: RE: [PATCH]irqchip/irq-gic-v3:Avoid a waste of LPI resource
 
> By the way I will finish my patch in the next week.

I rewrote the mechanism of lpis's management by using free list.
typedef struct lpi_mng {
       struct list_head lpi_list;
       int base;
       int len;
} lpi_mng_t;

When its_chunk_to_lpi is called, the entries of free list as below.
(Assumption id_bits = 30)
 base=8192, len=8192
 base=16384, len=16384
 base=32768, len=32768
 base=65536, len=65536
 base=131072, len=131072
 base=262144, len=262144
 base=524288, len=524288
 base=1048576, len=1048576
 base=2097152, len=2097152
 base=4194304, len=4194304
 base=8388608, len=8388608
 base=16777216, len=16777216
 base=33554432, len=33554432
 base=67108864, len=67108864
 base=134217728, len=134217728
 base=268435456, len=268435456
 base=536870912, len=536870912

When its_lpi_alloc_chunks is called, I split the free list until free list' length equal requested number of lpis.
I guarantee base is aligned on the size of len, and len is always a power of two.

Below is my patch for core ITS driver. 
Would you give me comments?

By the way,I wanted to add a parameter request_lpis_align.
But I think it is not really necessary.
Because if the number of lpis requested is 32, it will be allocated contiguous 32 lpis 
and the first lpi number allocated aligned on 32 even without this parameter.


-----------------
--- a/drivers/irqchip/irq-gic-v3-its.c
+++ b/drivers/irqchip/irq-gic-v3-its.c
@@ -672,82 +672,127 @@ static struct irq_chip its_irq_chip = {
        .irq_compose_msi_msg    = its_irq_compose_msi_msg,
 };

-/*
- * How we allocate LPIs:
- *
- * The GIC has id_bits bits for interrupt identifiers. From there, we
- * must subtract 8192 which are reserved for SGIs/PPIs/SPIs. Then, as
- * we allocate LPIs by chunks of 32, we can shift the whole thing by 5
- * bits to the right.
- *
- * This gives us (((1UL << id_bits) - 8192) >> 5) possible allocations.
- */
-#define IRQS_PER_CHUNK_SHIFT 5
-#define IRQS_PER_CHUNK         (1 << IRQS_PER_CHUNK_SHIFT)
-
-static unsigned long *lpi_bitmap;
-static u32 lpi_chunks;
-static DEFINE_SPINLOCK(lpi_lock);

-static int its_lpi_to_chunk(int lpi)
-{
-       return (lpi - 8192) >> IRQS_PER_CHUNK_SHIFT;
-}
+static struct list_head lpi_free_list;
+static struct list_head lpi_alloc_list;
+typedef struct lpi_mng {
+       struct list_head lpi_list;
+       int base;
+       int len;
+} lpi_mng_t;

-static int its_chunk_to_lpi(int chunk)
-{
-       return (chunk << IRQS_PER_CHUNK_SHIFT) + 8192;
-}
+static DEFINE_SPINLOCK(lpi_lock);

 static int __init its_lpi_init(u32 id_bits)
 {
-       lpi_chunks = its_lpi_to_chunk(1UL << id_bits);

-       lpi_bitmap = kzalloc(BITS_TO_LONGS(lpi_chunks) * sizeof(long),
-                            GFP_KERNEL);
-       if (!lpi_bitmap) {
-               lpi_chunks = 0;
+
+       u32 nr_irq = 1UL << id_bits;
+       lpi_mng_t *lpi_free_mng = NULL;
+       lpi_mng_t *lpi_new = NULL;
+       INIT_LIST_HEAD(&lpi_free_list);
+       INIT_LIST_HEAD(&lpi_alloc_list);
+
+       lpi_free_mng = kzalloc(sizeof(lpi_mng_t), GFP_ATOMIC);
+       if(!lpi_free_mng) {
                return -ENOMEM;
        }
+       lpi_free_mng->base = 0;
+       lpi_free_mng->len = nr_irq;
+       list_add(&lpi_free_mng->lpi_list, &lpi_free_list);
+
+       do {
+               lpi_free_mng = list_first_entry(&lpi_free_list, lpi_mng_t, lpi_list);
+               if(lpi_free_mng->len == 8192) {
+                       /*It is not lpi, so we delete */
+                       if(lpi_free_mng->base == 0) {
+                               list_del_init(&lpi_free_mng->lpi_list);
+                               kfree(lpi_free_mng);
+                               continue;
+                       }
+                       if(lpi_free_mng->base == 8192) {
+                               goto out;
+                       }
+               }
+               if(lpi_free_mng->len > 8192) {
+                       lpi_new  = kzalloc(sizeof (lpi_mng_t),
+                                        GFP_ATOMIC);
+                       if(!lpi_new) {
+                               return -ENOMEM;
+                       }
+                       lpi_free_mng->len /= 2;
+                       lpi_new->base = lpi_free_mng->base + lpi_free_mng->len;
+                       lpi_new->len = lpi_free_mng->len;
+                       list_add(&lpi_new->lpi_list,&lpi_free_mng->lpi_list);
+               }
+       }while(1);

-       pr_info("ITS: Allocated %d chunks for LPIs\n", (int)lpi_chunks);
+out:
+       pr_info("ITS: Allocated %d  LPIs\n", nr_irq - 8192);
        return 0;
 }

+static lpi_mng_t* its_alloc_lpi(int nr_irqs)
+{
+       lpi_mng_t *lpi_alloc_mng = NULL;
+       lpi_mng_t *lpi_split = NULL;
+       lpi_mng_t *lpi_new = NULL;
+       int base;
+
+       base = 0x7fffffff;
+       do {
+               list_for_each_entry(lpi_alloc_mng, &lpi_free_list, lpi_list) {
+                       if(nr_irqs > lpi_alloc_mng->len) {
+                               continue;
+                       }
+                       if(nr_irqs == lpi_alloc_mng->len) {
+                               list_del_init(&lpi_alloc_mng->lpi_list);
+                               list_add(&lpi_alloc_mng->lpi_list, &lpi_alloc_list);
+                               return lpi_alloc_mng;
+                       }
+                       if((nr_irqs < lpi_alloc_mng->len) && (lpi_alloc_mng->base < base)) {
+                               base = lpi_alloc_mng->base;
+                               lpi_split = lpi_alloc_mng;
+                       }
+               }
+               lpi_new  = kzalloc(sizeof (lpi_mng_t),
+                                GFP_ATOMIC);
+               if(!lpi_new || !lpi_split) {
+                       return NULL;
+               }
+
+               lpi_split->len /= 2;
+               lpi_new->base = lpi_split->base + lpi_split->len;
+               lpi_new->len = lpi_split->len;
+               list_add(&lpi_new->lpi_list,&lpi_split->lpi_list);
+
+       } while(1);
+}
+
 static unsigned long *its_lpi_alloc_chunks(int nr_irqs, int *base, int *nr_ids)
 {
        unsigned long *bitmap = NULL;
-       int chunk_id;
-       int nr_chunks;
-       int i;
-
-       nr_chunks = DIV_ROUND_UP(nr_irqs, IRQS_PER_CHUNK);
+       lpi_mng_t *lpi_alloc_mng = NULL;

        spin_lock(&lpi_lock);

-       do {
-               chunk_id = bitmap_find_next_zero_area(lpi_bitmap, lpi_chunks,
-                                                     0, nr_chunks, 0);
-               if (chunk_id < lpi_chunks)
-                       break;
-
-               nr_chunks--;
-       } while (nr_chunks > 0);
+       lpi_alloc_mng = its_alloc_lpi(nr_irqs);

-       if (!nr_chunks)
+       if (!lpi_alloc_mng)
                goto out;

-       bitmap = kzalloc(BITS_TO_LONGS(nr_chunks * IRQS_PER_CHUNK) * sizeof (long),
+       bitmap = kzalloc(BITS_TO_LONGS(nr_irqs) * sizeof (long),
                         GFP_ATOMIC);
        if (!bitmap)
                goto out;

-       for (i = 0; i < nr_chunks; i++)
-               set_bit(chunk_id + i, lpi_bitmap);

-       *base = its_chunk_to_lpi(chunk_id);
-       *nr_ids = nr_chunks * IRQS_PER_CHUNK;
+       *base = lpi_alloc_mng->base;
+       *nr_ids = lpi_alloc_mng->len;

 out:
        spin_unlock(&lpi_lock);
@@ -758,21 +803,47 @@ out:
        return bitmap;
 }

+static void its_joint_free_list(lpi_mng_t *free, lpi_mng_t *alloc)
+{
+       free->len = free->len * 2;
+       if(free->base > alloc->base) {
+               free->base = alloc->base;
+       }
+}
+
 static void its_lpi_free(struct event_lpi_map *map)
 {
        int base = map->lpi_base;
-       int nr_ids = map->nr_lpis;
-       int lpi;
-
+       lpi_mng_t *lpi_alloc_mng = NULL;
+       lpi_mng_t *lpi_free_mng = NULL;
+       bool first_half;
+       int pair_base;
        spin_lock(&lpi_lock);

-       for (lpi = base; lpi < (base + nr_ids); lpi += IRQS_PER_CHUNK) {
-               int chunk = its_lpi_to_chunk(lpi);
-               BUG_ON(chunk > lpi_chunks);
-               if (test_bit(chunk, lpi_bitmap)) {
-                       clear_bit(chunk, lpi_bitmap);
-               } else {
-                       pr_err("Bad LPI chunk %d\n", chunk);
+       list_for_each_entry(lpi_alloc_mng, &lpi_alloc_list, lpi_list) {
+               if(lpi_alloc_mng->base == base) {
+                       list_del_init(&lpi_alloc_mng->lpi_list);
+                       break;
+               }
+
+       }
+
+       first_half = (lpi_alloc_mng->base % (lpi_alloc_mng->len * 2)) ? false : true;
+       if(first_half) {
+               pair_base = lpi_alloc_mng->base + lpi_alloc_mng->len;
+       }else {
+               pair_base = lpi_alloc_mng->base - lpi_alloc_mng->len;
+       }
+
+       list_for_each_entry(lpi_free_mng, &lpi_free_list, lpi_list) {
+               if(lpi_free_mng->base == pair_base) {
+                       its_joint_free_list(lpi_free_mng, lpi_alloc_mng);
+                       kfree(lpi_alloc_mng);
+                       break;
+               }
+               if(lpi_alloc_mng->base  < lpi_free_mng->base) {
+                       list_add_tail(&lpi_alloc_mng->lpi_list, &lpi_free_mng->lpi_list);
+                       break;
                }
        }



Best Regards,
Lei Zhang
--
Lei Zhang  e-mail: zhang.lei at jp.fujitsu.com FUJITSU LIMITED

^ permalink raw reply

* [PATCH v2 2/2] KVM: arm/arm64: harden unmap_stage2_ptes in case end is not PAGE_SIZE aligned
From: Marc Zyngier @ 2018-05-18  9:48 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1526635630-18917-2-git-send-email-hejianet@gmail.com>

On 18/05/18 10:27, Jia He wrote:
> If it passes addr=0x202920000,size=0xfe00 to unmap_stage2_range->
> ...->unmap_stage2_ptes, unmap_stage2_ptes will get addr=0x202920000,
> end=0x20292fe00. After first while loop addr=0x202930000, end=0x20292fe00,
> then addr!=end. Thus it will touch another pages by put_pages() in the
> 2nd loop.
> 
> This patch fixes it by hardening the break condition of while loop.
> 
> Signed-off-by: jia.he at hxt-semitech.com
> ---
> v2: newly added
> 
>  virt/kvm/arm/mmu.c | 2 +-
>  1 file changed, 1 insertion(+), 1 deletion(-)
> 
> diff --git a/virt/kvm/arm/mmu.c b/virt/kvm/arm/mmu.c
> index 8dac311..45cd040 100644
> --- a/virt/kvm/arm/mmu.c
> +++ b/virt/kvm/arm/mmu.c
> @@ -217,7 +217,7 @@ static void unmap_stage2_ptes(struct kvm *kvm, pmd_t *pmd,
>  
>  			put_page(virt_to_page(pte));
>  		}
> -	} while (pte++, addr += PAGE_SIZE, addr != end);
> +	} while (pte++, addr += PAGE_SIZE, addr < end);
>  
>  	if (stage2_pte_table_empty(start_pte))
>  		clear_stage2_pmd_entry(kvm, pmd, start_addr);
> 

I don't think this change is the right thing to do. You get that failure
because you're being passed a size that is not a multiple of PAGE_SIZE.
That's the mistake.

You should ensure that this never happens, rather than changing the page
table walkers (which are consistent with the way this kind of code is
written in other places of the kernel). As you mentioned in your first
patch, the real issue is that KSM is broken, and this is what should be
fixed.

Thanks,

	M.
-- 
Jazz is not dead. It just smells funny...

^ permalink raw reply

* [PATCH v3 3/3] arm64: Introduce command line parameter to disable CNP
From: Vladimir Murzin @ 2018-05-18  9:46 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1526636765-11289-1-git-send-email-vladimir.murzin@arm.com>

There are cases when activating of Common Not Private (CNP) feature
might not be desirable; this patch allows to forcefully disable CNP
even it is supported by hardware.

Signed-off-by: Vladimir Murzin <vladimir.murzin@arm.com>
---
 Documentation/admin-guide/kernel-parameters.txt |  4 ++++
 arch/arm64/kernel/cpufeature.c                  | 11 ++++++++++-
 2 files changed, 14 insertions(+), 1 deletion(-)

diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt
index 1d1d53f..181ecca 100644
--- a/Documentation/admin-guide/kernel-parameters.txt
+++ b/Documentation/admin-guide/kernel-parameters.txt
@@ -2603,6 +2603,10 @@
 
 	noclflush	[BUGS=X86] Don't use the CLFLUSH instruction
 
+	nocnp		[ARM64]
+			Disable CNP (Common not Private translations)
+			even if it is supported by processor.
+
 	nodelayacct	[KNL] Disable per-task delay accounting
 
 	nodsp		[SH] Disable hardware DSP at boot time.
diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c
index 78de218..80fe8fa 100644
--- a/arch/arm64/kernel/cpufeature.c
+++ b/arch/arm64/kernel/cpufeature.c
@@ -826,6 +826,15 @@ static bool has_no_hw_prefetch(const struct arm64_cpu_capabilities *entry, int _
 		MIDR_CPU_VAR_REV(1, MIDR_REVISION_MASK));
 }
 
+static bool nocnp;
+
+static int __init early_nocnp(char *p)
+{
+	nocnp = true;
+	return 0;
+}
+early_param("nocnp", early_nocnp);
+
 static bool __maybe_unused
 has_useable_cnp(const struct arm64_cpu_capabilities *entry, int scope)
 {
@@ -833,7 +842,7 @@ has_useable_cnp(const struct arm64_cpu_capabilities *entry, int scope)
 	if (elfcorehdr_size)
 		return false;
 #endif
-	return has_cpuid_feature(entry, scope);
+	return has_cpuid_feature(entry, scope) && !nocnp;
 }
 
 static bool runs_at_el2(const struct arm64_cpu_capabilities *entry, int __unused)
-- 
2.0.0

^ permalink raw reply related

* [PATCH v3 2/3] arm64: KVM: Enable Common Not Private translations
From: Vladimir Murzin @ 2018-05-18  9:46 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1526636765-11289-1-git-send-email-vladimir.murzin@arm.com>

We rely on cpufeature framework to detect and enable CNP so for KVM we
need to patch hyp to set CNP bit just before TTBR0_EL2 gets written.

For the guest we encode CNP bit while building vttbr, so we don't need
to bother with that in a world switch.

Signed-off-by: Vladimir Murzin <vladimir.murzin@arm.com>
---
 arch/arm/include/asm/kvm_mmu.h   | 5 +++++
 arch/arm64/include/asm/kvm_mmu.h | 5 +++++
 arch/arm64/kvm/hyp-init.S        | 3 +++
 virt/kvm/arm/arm.c               | 4 ++--
 4 files changed, 15 insertions(+), 2 deletions(-)

diff --git a/arch/arm/include/asm/kvm_mmu.h b/arch/arm/include/asm/kvm_mmu.h
index de1b919..7a9d614 100644
--- a/arch/arm/include/asm/kvm_mmu.h
+++ b/arch/arm/include/asm/kvm_mmu.h
@@ -307,6 +307,11 @@ static inline int kvm_map_vectors(void)
 
 #define kvm_phys_to_vttbr(addr)		(addr)
 
+static inline bool kvm_cpu_has_cnp(void)
+{
+	return false;
+}
+
 #endif	/* !__ASSEMBLY__ */
 
 #endif /* __ARM_KVM_MMU_H__ */
diff --git a/arch/arm64/include/asm/kvm_mmu.h b/arch/arm64/include/asm/kvm_mmu.h
index 7faed6e..f8149d4 100644
--- a/arch/arm64/include/asm/kvm_mmu.h
+++ b/arch/arm64/include/asm/kvm_mmu.h
@@ -388,5 +388,10 @@ static inline int kvm_map_vectors(void)
 
 #define kvm_phys_to_vttbr(addr)		phys_to_ttbr(addr)
 
+static inline bool kvm_cpu_has_cnp(void)
+{
+	return system_supports_cnp();
+}
+
 #endif /* __ASSEMBLY__ */
 #endif /* __ARM64_KVM_MMU_H__ */
diff --git a/arch/arm64/kvm/hyp-init.S b/arch/arm64/kvm/hyp-init.S
index 5aa9ccf..2e7a93a 100644
--- a/arch/arm64/kvm/hyp-init.S
+++ b/arch/arm64/kvm/hyp-init.S
@@ -64,6 +64,9 @@ __do_hyp_init:
 	b.lo	__kvm_handle_stub_hvc
 
 	phys_to_ttbr x4, x0
+alternative_if ARM64_HAS_CNP
+	orr	x4, x4, #TTBR_CNP_BIT
+alternative_else_nop_endif
 	msr	ttbr0_el2, x4
 
 	mrs	x4, tcr_el1
diff --git a/virt/kvm/arm/arm.c b/virt/kvm/arm/arm.c
index 97d0ab2..a538ba3 100644
--- a/virt/kvm/arm/arm.c
+++ b/virt/kvm/arm/arm.c
@@ -470,7 +470,7 @@ static bool need_new_vmid_gen(struct kvm *kvm)
 static void update_vttbr(struct kvm *kvm)
 {
 	phys_addr_t pgd_phys;
-	u64 vmid;
+	u64 vmid, cnp = kvm_cpu_has_cnp() ? 1 : 0;
 
 	if (!need_new_vmid_gen(kvm))
 		return;
@@ -522,7 +522,7 @@ static void update_vttbr(struct kvm *kvm)
 	pgd_phys = virt_to_phys(kvm->arch.pgd);
 	BUG_ON(pgd_phys & ~VTTBR_BADDR_MASK);
 	vmid = ((u64)(kvm->arch.vmid) << VTTBR_VMID_SHIFT) & VTTBR_VMID_MASK(kvm_vmid_bits);
-	kvm->arch.vttbr = kvm_phys_to_vttbr(pgd_phys) | vmid;
+	kvm->arch.vttbr = kvm_phys_to_vttbr(pgd_phys) | vmid | cnp;
 
 	spin_unlock(&kvm_vmid_lock);
 
-- 
2.0.0

^ permalink raw reply related

* [PATCH v3 1/3] arm64: mm: Support Common Not Private translations
From: Vladimir Murzin @ 2018-05-18  9:46 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1526636765-11289-1-git-send-email-vladimir.murzin@arm.com>

Common Not Private (CNP) is a feature of ARMv8.2 extension which
allows translation table entries to be shared between different PEs in
the same inner shareable domain, so the hardware can use this fact to
optimise the caching of such entries in the TLB.

CNP occupies one bit in TTBRx_ELy and VTTBR_EL2, which advertises to
the hardware that the translation table entries pointed to by this
TTBR are the same as every PE in the same inner shareable domain for
which the equivalent TTBR also has CNP bit set. In case CNP bit is set
but TTBR does not point at the same translation table entries for a
given ASID and VMID, then the system is mis-configured, so the results
of translations are UNPREDICTABLE.

For EL1 we postpone setting CNP till all cpus are up and rely on
cpufeature framework to 1) patch the code which is sensitive to CNP
and 2) update TTBR1_EL1 with CNP bit set. TTBR1_EL1 can be
reprogrammed as result of hibernation or cpuidle (via __enable_mmu).
cpuidle's path has been changed to restore CnP and for hibernation the
code has been changed to save raw TTBR1_EL1 and blindly restore it on
resume.

For EL0 there are a few cases we need to care of changes in
TTBR0_EL1:
  - a switch to idmap
  - software emulated PAN

we rule out latter via Kconfig options and for the former we make
sure that CNP is set for non-zero ASIDs only.

Signed-off-by: Vladimir Murzin <vladimir.murzin@arm.com>
---
 arch/arm64/Kconfig                     | 13 +++++++++++++
 arch/arm64/include/asm/cpucaps.h       |  3 ++-
 arch/arm64/include/asm/cpufeature.h    |  6 ++++++
 arch/arm64/include/asm/mmu_context.h   | 12 ++++++++++++
 arch/arm64/include/asm/pgtable-hwdef.h |  2 ++
 arch/arm64/kernel/cpufeature.c         | 31 +++++++++++++++++++++++++++++++
 arch/arm64/kernel/hibernate.c          |  2 +-
 arch/arm64/kernel/suspend.c            |  4 ++++
 arch/arm64/mm/context.c                |  3 +++
 arch/arm64/mm/proc.S                   |  6 ++++++
 10 files changed, 80 insertions(+), 2 deletions(-)

diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig
index 75165d2..f1a8ce8 100644
--- a/arch/arm64/Kconfig
+++ b/arch/arm64/Kconfig
@@ -1130,6 +1130,19 @@ config ARM64_RAS_EXTN
 	  and access the new registers if the system supports the extension.
 	  Platform RAS features may additionally depend on firmware support.
 
+config ARM64_CNP
+	bool "Enable support for Common Not Private (CNP) translations"
+	depends on ARM64_PAN || !ARM64_SW_TTBR0_PAN
+	help
+	  Common Not Private (CNP) allows translation table entries to
+	  be shared between different PEs in the same inner shareable
+	  domain, so the hardware can use this fact to optimise the
+	  caching of such entries in the TLB.
+
+	  Selecting this option allows the CNP feature to be detected
+	  at runtime, and does not affect PEs that do not implement
+	  this feature.
+
 endmenu
 
 menu "ARMv8.3 architectural features"
diff --git a/arch/arm64/include/asm/cpucaps.h b/arch/arm64/include/asm/cpucaps.h
index b6ffe11..3ab63cc 100644
--- a/arch/arm64/include/asm/cpucaps.h
+++ b/arch/arm64/include/asm/cpucaps.h
@@ -51,7 +51,8 @@
 #define ARM64_HAS_ADDRESS_AUTH_ARCH		30
 #define ARM64_HAS_ADDRESS_AUTH_IMP_DEF		31
 #define ARM64_HAS_ADDRESS_AUTH			32
+#define ARM64_HAS_CNP				33
 
-#define ARM64_NCAPS				33
+#define ARM64_NCAPS				34
 
 #endif /* __ASM_CPUCAPS_H */
diff --git a/arch/arm64/include/asm/cpufeature.h b/arch/arm64/include/asm/cpufeature.h
index 060e3a4..fe160d4 100644
--- a/arch/arm64/include/asm/cpufeature.h
+++ b/arch/arm64/include/asm/cpufeature.h
@@ -280,6 +280,12 @@ static inline bool system_supports_sve(void)
 		cpus_have_const_cap(ARM64_SVE);
 }
 
+static inline bool system_supports_cnp(void)
+{
+	return IS_ENABLED(CONFIG_ARM64_CNP) &&
+		cpus_have_const_cap(ARM64_HAS_CNP);
+}
+
 /*
  * Read the pseudo-ZCR used by cpufeatures to identify the supported SVE
  * vector length.
diff --git a/arch/arm64/include/asm/mmu_context.h b/arch/arm64/include/asm/mmu_context.h
index 83eadbc..f80c1a9 100644
--- a/arch/arm64/include/asm/mmu_context.h
+++ b/arch/arm64/include/asm/mmu_context.h
@@ -149,6 +149,18 @@ static inline void cpu_replace_ttbr1(pgd_t *pgdp)
 
 	phys_addr_t pgd_phys = virt_to_phys(pgdp);
 
+	if (system_supports_cnp() && !WARN_ON(pgdp != lm_alias(swapper_pg_dir))) {
+		/*
+		 * cpu_replace_ttbr1() is used when there's a boot CPU
+		 * up (i.e. cpufeature framework is not up yet) and
+		 * latter only when we enable CNP via cpufeature's
+		 * enable() callback.
+                 * Also we rely on the cpu_hwcap bit being set before
+		 * calling the enable() function.
+		 */
+		pgd_phys |= TTBR_CNP_BIT;
+	}
+
 	replace_phys = (void *)__pa_symbol(idmap_cpu_replace_ttbr1);
 
 	cpu_install_idmap();
diff --git a/arch/arm64/include/asm/pgtable-hwdef.h b/arch/arm64/include/asm/pgtable-hwdef.h
index cdfe3e6..7294826 100644
--- a/arch/arm64/include/asm/pgtable-hwdef.h
+++ b/arch/arm64/include/asm/pgtable-hwdef.h
@@ -211,6 +211,8 @@
 #define PHYS_MASK_SHIFT		(CONFIG_ARM64_PA_BITS)
 #define PHYS_MASK		((UL(1) << PHYS_MASK_SHIFT) - 1)
 
+#define TTBR_CNP_BIT		(UL(1) << 0)
+
 /*
  * TCR flags.
  */
diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c
index 9d79c0f..78de218 100644
--- a/arch/arm64/kernel/cpufeature.c
+++ b/arch/arm64/kernel/cpufeature.c
@@ -20,6 +20,7 @@
 
 #include <linux/bsearch.h>
 #include <linux/cpumask.h>
+#include <linux/crash_dump.h>
 #include <linux/sort.h>
 #include <linux/stop_machine.h>
 #include <linux/types.h>
@@ -825,6 +826,16 @@ static bool has_no_hw_prefetch(const struct arm64_cpu_capabilities *entry, int _
 		MIDR_CPU_VAR_REV(1, MIDR_REVISION_MASK));
 }
 
+static bool __maybe_unused
+has_useable_cnp(const struct arm64_cpu_capabilities *entry, int scope)
+{
+#ifdef CONFIG_CRASH_DUMP
+	if (elfcorehdr_size)
+		return false;
+#endif
+	return has_cpuid_feature(entry, scope);
+}
+
 static bool runs_at_el2(const struct arm64_cpu_capabilities *entry, int __unused)
 {
 	return is_kernel_in_hyp_mode();
@@ -981,6 +992,14 @@ static bool has_address_auth(const struct arm64_cpu_capabilities *entry,
 }
 #endif /* CONFIG_ARM64_PTR_AUTH */
 
+#ifdef CONFIG_ARM64_CNP
+static int cpu_enable_cnp(void *__unused)
+{
+	cpu_replace_ttbr1(lm_alias(swapper_pg_dir));
+	return 0;
+}
+#endif
+
 static const struct arm64_cpu_capabilities arm64_features[] = {
 	{
 		.desc = "GIC system register CPU interface",
@@ -1086,6 +1105,18 @@ static const struct arm64_cpu_capabilities arm64_features[] = {
 		.sys_reg = SYS_ID_AA64ISAR1_EL1,
 		.field_pos = ID_AA64ISAR1_DPB_SHIFT,
 		.min_field_value = 1,
+#endif
+#ifdef CONFIG_ARM64_CNP
+	{
+		.desc = "Common not Private translations",
+		.capability = ARM64_HAS_CNP,
+		.def_scope = SCOPE_SYSTEM,
+		.matches = has_useable_cnp,
+		.sys_reg = SYS_ID_AA64MMFR2_EL1,
+		.sign = FTR_UNSIGNED,
+		.field_pos = ID_AA64MMFR2_CNP_SHIFT,
+		.min_field_value = 1,
+		.enable = cpu_enable_cnp,
 	},
 #endif
 #ifdef CONFIG_ARM64_SVE
diff --git a/arch/arm64/kernel/hibernate.c b/arch/arm64/kernel/hibernate.c
index 1ec5f28..ea27121 100644
--- a/arch/arm64/kernel/hibernate.c
+++ b/arch/arm64/kernel/hibernate.c
@@ -125,7 +125,7 @@ int arch_hibernation_header_save(void *addr, unsigned int max_size)
 		return -EOVERFLOW;
 
 	arch_hdr_invariants(&hdr->invariants);
-	hdr->ttbr1_el1		= __pa_symbol(swapper_pg_dir);
+	hdr->ttbr1_el1		= read_sysreg(ttbr1_el1);
 	hdr->reenter_kernel	= _cpu_resume;
 
 	/* We can't use __hyp_get_vectors() because kvm may still be loaded */
diff --git a/arch/arm64/kernel/suspend.c b/arch/arm64/kernel/suspend.c
index a307b9e..9576643 100644
--- a/arch/arm64/kernel/suspend.c
+++ b/arch/arm64/kernel/suspend.c
@@ -48,6 +48,10 @@ void notrace __cpu_suspend_exit(void)
 	 */
 	cpu_uninstall_idmap();
 
+	/* Restore CnP bit in TTBR1_EL1 */
+	if (system_supports_cnp())
+		cpu_replace_ttbr1(lm_alias(swapper_pg_dir));
+
 	/*
 	 * PSTATE was not saved over suspend/resume, re-enable any detected
 	 * features that might not have been set correctly.
diff --git a/arch/arm64/mm/context.c b/arch/arm64/mm/context.c
index becd77c..adc699a 100644
--- a/arch/arm64/mm/context.c
+++ b/arch/arm64/mm/context.c
@@ -222,6 +222,9 @@ void check_and_switch_context(struct mm_struct *mm, unsigned int cpu)
 	unsigned long flags;
 	u64 asid, old_active_asid;
 
+	if (system_supports_cnp())
+		cpu_set_reserved_ttbr0();
+
 	asid = atomic64_read(&mm->context.id);
 
 	/*
diff --git a/arch/arm64/mm/proc.S b/arch/arm64/mm/proc.S
index 868cd09..b9e39b8 100644
--- a/arch/arm64/mm/proc.S
+++ b/arch/arm64/mm/proc.S
@@ -159,6 +159,12 @@ ENTRY(cpu_do_switch_mm)
 	mrs	x2, ttbr1_el1
 	mmid	x1, x1				// get mm->context.id
 	phys_to_ttbr x3, x0
+
+alternative_if ARM64_HAS_CNP
+	cbz     x1, 1f                          // skip CNP for reserved ASID
+	orr     x3, x3, #TTBR_CNP_BIT
+1:
+alternative_else_nop_endif
 #ifdef CONFIG_ARM64_SW_TTBR0_PAN
 	bfi	x3, x1, #48, #16		// set the ASID field in TTBR0
 #endif
-- 
2.0.0

^ permalink raw reply related

* [PATCH v3 0/3]  Support Common Not Private translations
From: Vladimir Murzin @ 2018-05-18  9:46 UTC (permalink / raw)
  To: linux-arm-kernel

Common Not Private (CNP) translations is a feature of ARMv8.2
extension which allows translation table entries to be shared between
different PEs in the same inner shareable domain, so the hardware can
use this fact to optimise the caching of such entries in the TLB.

This patch set is an attempt to bring CNP support into Linux. It was
tested on a v8.2 Fast Model with exploring traces and checking that
TTBRx_ELy and VTTBR_EL2 have CnP bit set where appropriate.

Changelog:

	 v2 -> v3
	    - do not enable CNP if we are crush kernel (per James)
	    - default to "no"
	    - rebased on 4.17-rc4

  	 v1 -> v2
            - handle cpuilde case (per James)
	    - use lm_allias with swapper_pg_dir (per James)
            - rule out ARM64_SW_TTBR0_PAN case (per Catalin)
	    - s/BUG_ON/WARN_ON/ (per Catalin)
	    - comment and commit message updates (per Catalin)
	    - TTBR_CNP_BIT moved to asm/pgtable-hwdef.h (per Catalin)
	    - has_useable_cnp() simplified (per Julien)

	RFC -> v1
            - dropped RFC tag
            - rebased on 4.14-rc4

Thanks!

Vladimir Murzin (3):
  arm64: mm: Support Common Not Private translations
  arm64: KVM: Enable Common Not Private translations
  arm64: Introduce command line parameter to disable CNP

 Documentation/admin-guide/kernel-parameters.txt |  4 +++
 arch/arm/include/asm/kvm_mmu.h                  |  5 ++++
 arch/arm64/Kconfig                              | 13 ++++++++
 arch/arm64/include/asm/cpucaps.h                |  3 +-
 arch/arm64/include/asm/cpufeature.h             |  6 ++++
 arch/arm64/include/asm/kvm_mmu.h                |  5 ++++
 arch/arm64/include/asm/mmu_context.h            | 12 ++++++++
 arch/arm64/include/asm/pgtable-hwdef.h          |  2 ++
 arch/arm64/kernel/cpufeature.c                  | 40 +++++++++++++++++++++++++
 arch/arm64/kernel/hibernate.c                   |  2 +-
 arch/arm64/kernel/suspend.c                     |  4 +++
 arch/arm64/kvm/hyp-init.S                       |  3 ++
 arch/arm64/mm/context.c                         |  3 ++
 arch/arm64/mm/proc.S                            |  6 ++++
 virt/kvm/arm/arm.c                              |  4 +--
 15 files changed, 108 insertions(+), 4 deletions(-)

-- 
2.0.0

^ permalink raw reply

* [PATCH v2 26/26] arm64: dts: allwinner: a64: sopine: Enable HDMI output
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Enable HDMI output on sopine board.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 .../dts/allwinner/sun50i-a64-sopine-baseboard.dts  | 26 ++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64-sopine-baseboard.dts b/arch/arm64/boot/dts/allwinner/sun50i-a64-sopine-baseboard.dts
index abe179de35d7..72f29b78117c 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64-sopine-baseboard.dts
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64-sopine-baseboard.dts
@@ -61,6 +61,17 @@
 		stdout-path = "serial0:115200n8";
 	};
 
+	connector {
+		compatible = "hdmi-connector";
+		type = "a";
+
+		port {
+			hdmi_con_in: endpoint {
+				remote-endpoint = <&hdmi_out_con>;
+			};
+		};
+	};
+
 	reg_vcc1v8: vcc1v8 {
 		compatible = "regulator-fixed";
 		regulator-name = "vcc1v8";
@@ -69,6 +80,10 @@
 	};
 };
 
+&de {
+	status = "okay";
+};
+
 &ehci0 {
 	status = "okay";
 };
@@ -86,6 +101,17 @@
 	status = "okay";
 };
 
+&hdmi {
+	hvcc-supply = <&reg_dldo1>;
+	status = "okay";
+};
+
+&hdmi_out {
+	hdmi_out_con: endpoint {
+		remote-endpoint = <&hdmi_con_in>;
+	};
+};
+
 &mdio {
 	ext_rgmii_phy: ethernet-phy at 1 {
 		compatible = "ethernet-phy-ieee802.3-c22";
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 25/26] arm64: dts: allwinner: a64: pine64: Enable HDMI output
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Enable HDMI output on pine64 board.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 .../arm64/boot/dts/allwinner/sun50i-a64-pine64.dts | 26 ++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64-pine64.dts b/arch/arm64/boot/dts/allwinner/sun50i-a64-pine64.dts
index a75825798a71..a4ec0900a885 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64-pine64.dts
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64-pine64.dts
@@ -62,6 +62,21 @@
 	chosen {
 		stdout-path = "serial0:115200n8";
 	};
+
+	connector {
+		compatible = "hdmi-connector";
+		type = "a";
+
+		port {
+			hdmi_con_in: endpoint {
+				remote-endpoint = <&hdmi_out_con>;
+			};
+		};
+	};
+};
+
+&de {
+	status = "okay";
 };
 
 &ehci0 {
@@ -82,6 +97,17 @@
 
 };
 
+&hdmi {
+	hvcc-supply = <&reg_dldo1>;
+	status = "okay";
+};
+
+&hdmi_out {
+	hdmi_out_con: endpoint {
+		remote-endpoint = <&hdmi_con_in>;
+	};
+};
+
 &i2c1 {
 	pinctrl-names = "default";
 	pinctrl-0 = <&i2c1_pins>;
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 24/26] arm64: dts: allwinner: a64: a64-olinuxino: Enable HDMI output
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Enable HDMI output on a64-olinuxino board.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 .../boot/dts/allwinner/sun50i-a64-olinuxino.dts    | 26 ++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64-olinuxino.dts b/arch/arm64/boot/dts/allwinner/sun50i-a64-olinuxino.dts
index 3b3081b10ecb..83329c8fec4f 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64-olinuxino.dts
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64-olinuxino.dts
@@ -58,12 +58,38 @@
 		stdout-path = "serial0:115200n8";
 	};
 
+	connector {
+		compatible = "hdmi-connector";
+		type = "a";
+
+		port {
+			hdmi_con_in: endpoint {
+				remote-endpoint = <&hdmi_out_con>;
+			};
+		};
+	};
+
 	wifi_pwrseq: wifi_pwrseq {
 		compatible = "mmc-pwrseq-simple";
 		reset-gpios = <&r_pio 0 2 GPIO_ACTIVE_LOW>; /* PL2 */
 	};
 };
 
+&de {
+	status = "okay";
+};
+
+&hdmi {
+	hvcc-supply = <&reg_dldo1>;
+	status = "okay";
+};
+
+&hdmi_out {
+	hdmi_out_con: endpoint {
+		remote-endpoint = <&hdmi_con_in>;
+	};
+};
+
 &mmc0 {
 	pinctrl-names = "default";
 	pinctrl-0 = <&mmc0_pins>;
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 23/26] arm64: dts: allwinner: a64: orangepi-win: Enable HDMI output
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Enable HDMI output on Orangepi-win board.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 .../boot/dts/allwinner/sun50i-a64-orangepi-win.dts | 26 ++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64-orangepi-win.dts b/arch/arm64/boot/dts/allwinner/sun50i-a64-orangepi-win.dts
index bf42690a3361..b6fdd052d473 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64-orangepi-win.dts
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64-orangepi-win.dts
@@ -57,12 +57,38 @@
 	chosen {
 		stdout-path = "serial0:115200n8";
 	};
+
+	connector {
+		compatible = "hdmi-connector";
+		type = "a";
+
+		port {
+			hdmi_con_in: endpoint {
+				remote-endpoint = <&hdmi_out_con>;
+			};
+		};
+	};
+};
+
+&de {
+	status = "okay";
 };
 
 &ehci1 {
 	status = "okay";
 };
 
+&hdmi {
+	hvcc-supply = <&reg_dldo1>;
+	status = "okay";
+};
+
+&hdmi_out {
+	hdmi_out_con: endpoint {
+		remote-endpoint = <&hdmi_con_in>;
+	};
+};
+
 &mmc0 {
 	pinctrl-names = "default";
 	pinctrl-0 = <&mmc0_pins>;
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 22/26] arm64: dts: allwinner: a64: nanopi-a64: Enable HDMI output
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Enable HDMI output on nanopi-a64 board.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 .../boot/dts/allwinner/sun50i-a64-nanopi-a64.dts   | 26 ++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64-nanopi-a64.dts b/arch/arm64/boot/dts/allwinner/sun50i-a64-nanopi-a64.dts
index e2dce48fa29a..19fe7eed45e9 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64-nanopi-a64.dts
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64-nanopi-a64.dts
@@ -57,6 +57,21 @@
 	chosen {
 		stdout-path = "serial0:115200n8";
 	};
+
+	connector {
+		compatible = "hdmi-connector";
+		type = "a";
+
+		port {
+			hdmi_con_in: endpoint {
+				remote-endpoint = <&hdmi_out_con>;
+			};
+		};
+	};
+};
+
+&de {
+	status = "okay";
 };
 
 &ehci0 {
@@ -67,6 +82,17 @@
 	status = "okay";
 };
 
+&hdmi {
+	hvcc-supply = <&reg_dldo1>;
+	status = "okay";
+};
+
+&hdmi_out {
+	hdmi_out_con: endpoint {
+		remote-endpoint = <&hdmi_con_in>;
+	};
+};
+
 /* i2c1 connected with gpio headers like pine64, bananapi */
 &i2c1 {
 	pinctrl-names = "default";
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 21/26] arm64: dts: allwinner: a64: bananapi-m64: Enable HDMI output
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Enable HDMI output on Bananpi-m64 board.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 .../boot/dts/allwinner/sun50i-a64-bananapi-m64.dts | 26 ++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64-bananapi-m64.dts b/arch/arm64/boot/dts/allwinner/sun50i-a64-bananapi-m64.dts
index 0716b1441187..bbbf7b17b70b 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64-bananapi-m64.dts
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64-bananapi-m64.dts
@@ -60,6 +60,17 @@
 		stdout-path = "serial0:115200n8";
 	};
 
+	connector {
+		compatible = "hdmi-connector";
+		type = "a";
+
+		port {
+			hdmi_con_in: endpoint {
+				remote-endpoint = <&hdmi_out_con>;
+			};
+		};
+	};
+
 	leds {
 		compatible = "gpio-leds";
 
@@ -86,6 +97,10 @@
 	};
 };
 
+&de {
+	status = "okay";
+};
+
 &ehci0 {
 	status = "okay";
 };
@@ -103,6 +118,17 @@
 	status = "okay";
 };
 
+&hdmi {
+	hvcc-supply = <&reg_dldo1>;
+	status = "okay";
+};
+
+&hdmi_out {
+	hdmi_out_con: endpoint {
+		remote-endpoint = <&hdmi_con_in>;
+	};
+};
+
 &i2c1 {
 	pinctrl-names = "default";
 	pinctrl-0 = <&i2c1_pins>;
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 20/26] drm: sun4i: add support for HVCC regulator for DWC HDMI glue
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

From: Icenowy Zheng <icenowy@aosc.io>

Allwinner SoCs with DWC HDMI controller have a "HVCC" power pin for the
HDMI part, and on some boards it's connected to a dedicated regulator
rather than the main 3.3v.

Add support for optional HVCC regulator. For boards that doesn't use a
dedicated regulator to power it, the default dummy regulator is used.

Signed-off-by: Icenowy Zheng <icenowy@aosc.io>
Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 drivers/gpu/drm/sun4i/sun8i_dw_hdmi.c | 14 ++++++++++++++
 drivers/gpu/drm/sun4i/sun8i_dw_hdmi.h |  2 ++
 2 files changed, 16 insertions(+)

diff --git a/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.c b/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.c
index 9f40a44b456b..7c33faff7ad4 100644
--- a/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.c
+++ b/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.c
@@ -73,6 +73,12 @@ static int sun8i_dw_hdmi_bind(struct device *dev, struct device *master,
 	if (encoder->possible_crtcs == 0)
 		return -EPROBE_DEFER;
 
+	hdmi->vcc_hdmi = devm_regulator_get(dev, "hvcc");
+	if (IS_ERR(hdmi->vcc_hdmi)) {
+		dev_err(dev, "Could not get HDMI power supply\n");
+		return PTR_ERR(hdmi->vcc_hdmi);
+	}
+
 	hdmi->rst_ctrl = devm_reset_control_get(dev, "ctrl");
 	if (IS_ERR(hdmi->rst_ctrl)) {
 		dev_err(dev, "Could not get ctrl reset control\n");
@@ -91,6 +97,12 @@ static int sun8i_dw_hdmi_bind(struct device *dev, struct device *master,
 		return ret;
 	}
 
+	ret = regulator_enable(hdmi->vcc_hdmi);
+	if (ret) {
+		dev_err(dev, "Cannot enable HDMI power supply\n");
+		goto err_disable_vcc;
+	}
+
 	ret = clk_prepare_enable(hdmi->clk_tmds);
 	if (ret) {
 		dev_err(dev, "Could not enable tmds clock\n");
@@ -143,6 +155,8 @@ static int sun8i_dw_hdmi_bind(struct device *dev, struct device *master,
 	clk_disable_unprepare(hdmi->clk_tmds);
 err_assert_ctrl_reset:
 	reset_control_assert(hdmi->rst_ctrl);
+err_disable_vcc:
+	regulator_disable(hdmi->vcc_hdmi);
 
 	return ret;
 }
diff --git a/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.h b/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.h
index 303189d6602c..65366eeb38d8 100644
--- a/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.h
+++ b/drivers/gpu/drm/sun4i/sun8i_dw_hdmi.h
@@ -10,6 +10,7 @@
 #include <drm/drm_encoder.h>
 #include <linux/clk.h>
 #include <linux/regmap.h>
+#include <linux/regulator/consumer.h>
 #include <linux/reset.h>
 
 #define SUN8I_HDMI_PHY_DBG_CTRL_REG	0x0000
@@ -175,6 +176,7 @@ struct sun8i_dw_hdmi {
 	struct drm_encoder		encoder;
 	struct sun8i_hdmi_phy		*phy;
 	struct dw_hdmi_plat_data	plat_data;
+	struct regulator		*vcc_hdmi;
 	struct reset_control		*rst_ctrl;
 };
 
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 19/26] arm64: dts: allwinner: a64: Add HDMI pipeline
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

HDMI pipeline on Allwinner A64 has similar behavior like A83T
where tcon1 is connected to HDMI.

Setup the pipeline according to that.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- none

 arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi | 21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi b/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi
index 4ffd4787acd2..8ec6559d10cc 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi
@@ -257,6 +257,10 @@
 					#size-cells = <0>;
 					reg = <1>;
 
+					tcon1_out_hdmi: endpoint at 1 {
+						reg = <1>;
+						remote-endpoint = <&hdmi_in_tcon1>;
+					};
 				};
 			};
 		};
@@ -719,6 +723,23 @@
 			phys = <&hdmi_phy>;
 			phy-names = "hdmi-phy";
 			status = "disabled";
+
+			ports {
+				#address-cells = <1>;
+				#size-cells = <0>;
+
+				hdmi_in: port at 0 {
+					reg = <0>;
+
+					hdmi_in_tcon1: endpoint {
+						remote-endpoint = <&tcon1_out_hdmi>;
+					};
+				};
+
+				hdmi_out: port at 1 {
+					reg = <1>;
+				};
+			};
 		};
 
 		hdmi_phy: hdmi-phy at 1ef0000 {
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 18/26] drm/sun4i: Enable DesignWare HDMI for SUN8I and SUN50I
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Allwinner SoC like SUN8I and SUN50I are now using DesignWare HDMI
so enable them as default.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- Enable for SUN8I

 drivers/gpu/drm/sun4i/Kconfig | 1 +
 1 file changed, 1 insertion(+)

diff --git a/drivers/gpu/drm/sun4i/Kconfig b/drivers/gpu/drm/sun4i/Kconfig
index a84120025197..c10617c1f84b 100644
--- a/drivers/gpu/drm/sun4i/Kconfig
+++ b/drivers/gpu/drm/sun4i/Kconfig
@@ -52,6 +52,7 @@ config DRM_SUN6I_DSI
 
 config DRM_SUN8I_DW_HDMI
 	tristate "Support for Allwinner version of DesignWare HDMI"
+	default MACH_SUN8I || (ARM64 && ARCH_SUNXI)
 	depends on DRM_SUN4I
 	select DRM_DW_HDMI
 	help
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 17/26] arm64: dts: allwinner: a64: Add HDMI support
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

HDMI on Allwinner A64 has similar behaviour like H3/H5/A83T, so
reuse the same dts node details for A64 with A83T compatible
as fallback.

HDMI PHY on Allwinner A64 has two clock parents so add them
as pll-0 and pll-1 in CCU clock phadles.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- Change compatibles and other based on previous patch changes

 arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi | 27 +++++++++++++++++++++++++++
 1 file changed, 27 insertions(+)

diff --git a/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi b/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi
index 9c1452ee8027..4ffd4787acd2 100644
--- a/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi
+++ b/arch/arm64/boot/dts/allwinner/sun50i-a64.dtsi
@@ -705,6 +705,33 @@
 			#interrupt-cells = <3>;
 		};
 
+		hdmi: hdmi at 1ee0000 {
+			compatible = "allwinner,sun50i-a64-dw-hdmi",
+				     "allwinner,sun8i-a83t-dw-hdmi";
+			reg = <0x01ee0000 0x10000>;
+			reg-io-width = <1>;
+			interrupts = <GIC_SPI 88 IRQ_TYPE_LEVEL_HIGH>;
+			clocks = <&ccu CLK_BUS_HDMI>, <&ccu CLK_HDMI_DDC>,
+				 <&ccu CLK_HDMI>;
+			clock-names = "iahb", "isfr", "tmds";
+			resets = <&ccu RST_BUS_HDMI1>;
+			reset-names = "ctrl";
+			phys = <&hdmi_phy>;
+			phy-names = "hdmi-phy";
+			status = "disabled";
+		};
+
+		hdmi_phy: hdmi-phy at 1ef0000 {
+			compatible = "allwinner,sun50i-a64-hdmi-phy";
+			reg = <0x01ef0000 0x10000>;
+			clocks = <&ccu CLK_BUS_HDMI>, <&ccu CLK_HDMI_DDC>,
+				 <&ccu CLK_PLL_VIDEO0>, <&ccu CLK_PLL_VIDEO1>;
+			clock-names = "bus", "mod", "pll-0", "pll-1";
+			resets = <&ccu RST_BUS_HDMI0>;
+			reset-names = "phy";
+			#phy-cells = <0>;
+		};
+
 		rtc: rtc at 1f00000 {
 			compatible = "allwinner,sun6i-a31-rtc";
 			reg = <0x01f00000 0x54>;
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 16/26] dt-bindings: clock: sun50i-a64-ccu: Add PLL_VIDEO[0-1] macros
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

Allwinner A64 has two clock parents PLL_VIDEO0 and PLL_VIDEO1.

Include these macros on dt-bindings so-that the same can be
used while defining CCU clock phadles.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- new patch

 include/dt-bindings/clock/sun50i-a64-ccu.h | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/include/dt-bindings/clock/sun50i-a64-ccu.h b/include/dt-bindings/clock/sun50i-a64-ccu.h
index d66432c6e675..d1d7d5b7d06a 100644
--- a/include/dt-bindings/clock/sun50i-a64-ccu.h
+++ b/include/dt-bindings/clock/sun50i-a64-ccu.h
@@ -43,7 +43,9 @@
 #ifndef _DT_BINDINGS_CLK_SUN50I_A64_H_
 #define _DT_BINDINGS_CLK_SUN50I_A64_H_
 
+#define CLK_PLL_VIDEO0		7
 #define CLK_PLL_PERIPH0		11
+#define CLK_PLL_VIDEO1		15
 
 #define CLK_BUS_MIPI_DSI	28
 #define CLK_BUS_CE		29
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 15/26] dt-bindings: display: Add compatible for A64 HDMI PHY
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

HDMI PHY on Allwinner A64 has similar like H3/H5 but with
two clock parents, so add separate compatible for A64.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- Add separate compatible for A64

 Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt b/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt
index 1a5ff416dea4..4f7b9dca8ca0 100644
--- a/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt
+++ b/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt
@@ -104,6 +104,7 @@ Required properties:
   - compatible: value must be one of:
     * allwinner,sun8i-a83t-hdmi-phy
     * allwinner,sun8i-h3-hdmi-phy
+    * allwinner,sun50i-a64-hdmi-phy
   - reg: base address and size of memory-mapped region
   - clocks: phandles to the clocks feeding the HDMI PHY
     * bus: the HDMI PHY interface clock
-- 
2.14.3

^ permalink raw reply related

* [PATCH v2 14/26] dt-bindings: display: Add compatible for A64 HDMI
From: Jagan Teki @ 2018-05-18  9:45 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20180518094536.17201-1-jagan@amarulasolutions.com>

HDMI on Allwinner A64 has similar like H3/H5/A83T.

Add compatible a64 and update A83T compatible as fallback.

Signed-off-by: Jagan Teki <jagan@amarulasolutions.com>
---
Changes for v2:
- Add fallback compatible

 Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt b/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt
index 863afad6a4df..1a5ff416dea4 100644
--- a/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt
+++ b/Documentation/devicetree/bindings/display/sunxi/sun4i-drm.txt
@@ -78,6 +78,7 @@ Required properties:
 
   - compatible: value must be one of:
     * "allwinner,sun8i-a83t-dw-hdmi"
+    * "allwinner,sun50i-a64-dw-hdmi", "allwinner,sun8i-a83t-dw-hdmi"
   - reg: base address and size of memory-mapped region
   - reg-io-width: See dw_hdmi.txt. Shall be 1.
   - interrupts: HDMI interrupt number
-- 
2.14.3

^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox