* [PATCH v2 3/3] spi: pca2xx-pci: Allow MSI
From: Jarkko Nikula @ 2017-01-17 11:18 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484593718.2133.156.camel@linux.intel.com>
On 01/16/2017 09:08 PM, Andy Shevchenko wrote:
> On Mon, 2017-01-16 at 19:44 +0100, Jan Kiszka wrote:
>> Now that the core is ready for edge-triggered interrupts, we can
>> safely
>> allow the PCI versions that provide this to enable the feature and,
>> thus, have less shared interrupts.
>>
>
> Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
>
I was looking at is there need to call pci_free_irq_vectors() but
pcim_release() takes care of that since this driver uses
pcim_enable_device().
Reviewed-by: Jarkko Nikula <jarkko.nikula@linux.intel.com>
^ permalink raw reply
* [PATCH v3 1/2] of: base: add support to find the level of the last cache
From: Will Deacon @ 2017-01-17 11:30 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484563244-14743-1-git-send-email-sudeep.holla@arm.com>
On Mon, Jan 16, 2017 at 10:40:43AM +0000, Sudeep Holla wrote:
> It is useful to have helper function just to get the number of cache
> levels for a given logical cpu. We can obtain the same by just checking
> the level at which the last cache is present. This patch adds support
> to find the level of the last cache for a given cpu.
>
> It will be used on ARM64 platform where the device tree provides the
> information for the additional non-architected/transparent/external
> last level caches that are not integrated with the processors.
>
> Cc: Mark Rutland <mark.rutland@arm.com>
> Suggested-by: Rob Herring <robh+dt@kernel.org>
> Acked-by: Rob Herring <robh+dt@kernel.org>
> Tested-by: Tan Xiaojun <tanxiaojun@huawei.com>
> Signed-off-by: Sudeep Holla <sudeep.holla@arm.com>
> ---
> drivers/of/base.c | 26 ++++++++++++++++++++++++++
> include/linux/of.h | 1 +
> 2 files changed, 27 insertions(+)
Thanks, I've queued these two for 4.11.
Will
^ permalink raw reply
* [PATCH 1/2] dt-bindings: gpu: Add Mali Utgard bindings
From: Krzysztof Kozlowski @ 2017-01-17 11:31 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20170117093813.mxp2hgoxbgske6ru@lukather>
On Tue, Jan 17, 2017 at 11:38 AM, Maxime Ripard
<maxime.ripard@free-electrons.com> wrote:
> Hi,
>
> On Mon, Jan 16, 2017 at 08:49:06PM +0200, Krzysztof Kozlowski wrote:
>> On Mon, Jan 16, 2017 at 02:24:23PM +0100, Maxime Ripard wrote:
>> > The ARM Mali Utgard GPU family is embedded into a number of SoCs from
>> > Allwinner, Amlogic, Mediatek or Rockchip.
>> >
>> > Add a binding for the GPU of that family.
>> >
>> > Signed-off-by: Maxime Ripard <maxime.ripard@free-electrons.com>
>> > ---
>> > .../devicetree/bindings/gpu/arm,mali-utgard.txt | 76 ++++++++++++++++++++++
>> > 1 file changed, 76 insertions(+)
>> > create mode 100644 Documentation/devicetree/bindings/gpu/arm,mali-utgard.txt
>>
>> Do you have a driver in kernel which will implement these bindings?
>
> No, but we have bindings for out-of-tree drivers already.
>
>> Defining them for out-of-tree driver does not bring any benefits
>> (3rd party driver will not respect them anyway).
>
> You could see it the other way around too. The out-of-tree drivers
> don't respect it at the moment because there's no binding to respect.
Indeed, that's a point. However valid only when the out-of-tree driver
will respect them, for example do not break them on next release.
Best regards,
Krzysztof
^ permalink raw reply
* [PATCH 1/2] dt-bindings: gpu: Add Mali Utgard bindings
From: Krzysztof Kozlowski @ 2017-01-17 11:33 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <4f5b8608-af6c-3ef5-aaf0-e7e034d006cd@baylibre.com>
On Tue, Jan 17, 2017 at 12:22 PM, Neil Armstrong
<narmstrong@baylibre.com> wrote:
> On 01/17/2017 10:38 AM, Maxime Ripard wrote:
>> Hi,
>>
>> On Mon, Jan 16, 2017 at 08:49:06PM +0200, Krzysztof Kozlowski wrote:
>>> On Mon, Jan 16, 2017 at 02:24:23PM +0100, Maxime Ripard wrote:
>>>> The ARM Mali Utgard GPU family is embedded into a number of SoCs from
>>>> Allwinner, Amlogic, Mediatek or Rockchip.
>>>>
>>>> Add a binding for the GPU of that family.
>>>>
>>>> Signed-off-by: Maxime Ripard <maxime.ripard@free-electrons.com>
>>>> ---
>>>> .../devicetree/bindings/gpu/arm,mali-utgard.txt | 76 ++++++++++++++++++++++
>>>> 1 file changed, 76 insertions(+)
>>>> create mode 100644 Documentation/devicetree/bindings/gpu/arm,mali-utgard.txt
>>>
>>> Do you have a driver in kernel which will implement these bindings?
>>
>> No, but we have bindings for out-of-tree drivers already.
>>
>>> Defining them for out-of-tree driver does not bring any benefits
>>> (3rd party driver will not respect them anyway).
>>
>> You could see it the other way around too. The out-of-tree drivers
>> don't respect it at the moment because there's no binding to respect.
>>
>> And at least for us, we definitely plan on doing that.
>>
>> Maxime
>
> Hi Maxime, Krzysztof,
>
> We hope this will be accepted so it will solve the same issue we have on Amlogic SoCs
> and all the other mali powered SoCs.
It will be helpful also for other SoCs using Mali 400 (e.g.
Exynos3250, Exynos4412).
> Having mainline bindings will forcre out-of-tree driver to respect those bindings
> and remove a dts out-of-tree patch aswell.
I would argue here over the word "force". Having bindings defined here
does not force anyone into anything. The out-of-tree can do whatever
they want. It is a wish from kernel side - it might be respected but
it might not.
Just to be sure - I am not opposed against. Some time ago I wanted
Mali400 to be upstreamed but with current policy about user-space side
it is not possible.
Best regards,
Krzysztof
^ permalink raw reply
* [PATCH v3 2/3] arm64: dts: juno: fix CoreSight support for Juno r1/r2 variants
From: Sudeep Holla @ 2017-01-17 11:37 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CAOesGMj_23cehRP0ftdM_+Wvuj3tUWi5T5+w5z5v62zfkLu9+w@mail.gmail.com>
On 17/01/17 06:58, Olof Johansson wrote:
> Hi,
>
> On Thu, Jan 12, 2017 at 7:20 AM, Sudeep Holla <sudeep.holla@arm.com> wrote:
>> From: Mike Leach <mike.leach@linaro.org>
>>
>> The CoreSight support added for Juno is valid for only Juno r0.
>> The Juno r1 and r2 variants have additional components and alternative
>> connection routes between trace source and sinks.
>>
>> This patch builds on top of the existing r0 support and extends it to
>> Juno r1/r2 variants.
>>
>> Signed-off-by: Mike Leach <mike.leach@linaro.org>
>> [sudeep.holla at arm.com: minor changelog update and reorganising the common
>> coresight components back into juno-base.dtsi to avoid duplication]
>> Signed-off-by: Sudeep Holla <sudeep.holla@arm.com>
>> ---
>> arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi | 102 ++++++++++++++++++++++++++++++
>> arch/arm64/boot/dts/arm/juno-r1.dts | 9 +++
>> arch/arm64/boot/dts/arm/juno-r2.dts | 9 +++
>> 3 files changed, 120 insertions(+)
>> create mode 100644 arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi
>>
>> diff --git a/arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi b/arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi
>> new file mode 100644
>> index 000000000000..89fcef366ff9
>> --- /dev/null
>> +++ b/arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi
>> @@ -0,0 +1,102 @@
>> + csys1_funnel at 20130000 {
>> + compatible = "arm,coresight-funnel", "arm,primecell";
>> + reg = <0 0x20130000 0 0x1000>;
>> +
>> + clocks = <&soc_smc50mhz>;
>> + clock-names = "apb_pclk";
>> + power-domains = <&scpi_devpd 0>;
>> + ports {
>> + #address-cells = <1>;
>> + #size-cells = <0>;
>> +
>> + /* input port */
>> + port at 0 {
>> + reg = <0>;
>> + csys1_funnel_out_port: endpoint {
>> + remote-endpoint =
>> + <&etf1_in_port>;
>> + };
>> + };
>> +
>> + /* output port */
>> + port at 1 {
>> + reg = <0>;
>> + csys1_funnel_in_port0: endpoint {
>> + slave-mode;
>> + };
>> + };
>> +
>> + };
>> + };
>> +
>> + etf1 at 20140000 {
>
> The concept behind device-tree is that you name the nodes based on the
> type of device they are. "i2c", "ethernet", etc. Not "eth0", "i2c3",
> and so on.
>
> So, this should probably be something else than "etf1", and the
> etf->etf0 rename you did somewhere else shouldn't be made either.
>
Agreed, will fix it. Sorry for not noticing that before. I somehow
always confused them to be labels rather that node names and even missed
to observe that when I changed for R0.
[...]
>> diff --git a/arch/arm64/boot/dts/arm/juno-r1.dts b/arch/arm64/boot/dts/arm/juno-r1.dts
>> index eec37feee8fc..d4b85d9d343e 100644
>> --- a/arch/arm64/boot/dts/arm/juno-r1.dts
>> +++ b/arch/arm64/boot/dts/arm/juno-r1.dts
>> @@ -178,6 +178,7 @@
>> };
>>
>> #include "juno-base.dtsi"
>> + #include "juno-cs-r1r2.dtsi"
>
> Please don't nest dtsi inside a structure like this. We normally let
> them stand by themselves at the top of the file instead.
>
> (yes, please fix for juno-base too).
Agreed and fixed locally, will post it as part of v4.
--
Regards,
Sudeep
^ permalink raw reply
* [Question] A question about arm64 pte
From: Catalin Marinas @ 2017-01-17 11:45 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <ecf2bd9f-9f96-0e6d-564d-93cff5bbf0cb@huawei.com>
On Tue, Jan 17, 2017 at 11:53:43AM +0800, Yisheng Xie wrote:
> On 2017/1/16 22:36, Catalin Marinas wrote:
> > On Mon, Jan 16, 2017 at 08:39:56PM +0800, Yisheng Xie wrote:
> >> On 2017/1/16 19:56, Catalin Marinas wrote:
> >>> On Mon, Jan 16, 2017 at 06:08:47PM +0800, Yisheng Xie wrote:
> >>>
> >> However?when use memset to write the region it still works well, and
> >> the bit PTE_RDONLY is also cleared. Is there anywhere clear the
> >> PTE_RDONLY before write that page ?
> >
> > See handle_pte_fault(). On the first access to a writable+clean page
> > (PTE_WRITE set, PTE_RDONLY set, PTE_DIRTY cleared), the kernel traps it
> > and, if pte_write() is true (your case), it calls pte_mkdirty(). The
> > subsequently called ptep_set_access_flags() function would clear
> > PTE_RDONLY, giving you a writable mapping.
>
> Sorry to disturb, but why page fault will happened here, for pte already
> present with AF bit set?
>
> Here is what I get when mmap a reserved memory region 0x39ef 0000~0x3a00 0000
> use /dev/mem:
> [ 442.704228] pgd = ffff802785f14000
> [ 442.707641] [ffff86e4b000] *pgd=000000279080c003, *pud=0000002785f01003, *pmd=0000002783f5b003, *pte=0168000039ef0fd3
The pte seems to have bit 7 set: PTE_RDONLY. So you would get a fault on
write (but not read). Since PTE_WRITE is also set, handle_pte_fault()
will mark the entry as dirty (bit 55, cleared above) and clear
PTE_RDONLY before restarting the access instruction. User space wouldn't
notice, just a slight delay on the first access.
--
Catalin
^ permalink raw reply
* [PATCH v29 3/9] arm64: kdump: reserve memory for crash dump kernel
From: Mark Rutland @ 2017-01-17 11:54 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20170117082043.GM20972@linaro.org>
On Tue, Jan 17, 2017 at 05:20:44PM +0900, AKASHI Takahiro wrote:
> On Fri, Jan 13, 2017 at 11:39:15AM +0000, Mark Rutland wrote:
> > Great! I think it would be better to follow the approach of
> > mark_rodata_ro(), rather than opening up set_memory_*(), but otherwise,
> > it looks like it should work.
>
> I'm not quite sure what the approach of mark_rodata_ro() means, but
> I found that using create_mapping_late() may cause two problems:
>
> 1) it fails when PTE_CONT bits mismatch between an old and new mmu entry.
> This can happen, say, if the memory range for crash dump kernel
> starts in the mid of _continuous_ pages.
That should only happen if we try to remap a segment different to what
we originally mapped.
I was intending that we'd explicitly map the reserved region separately
in the boot path, like we do for kernel segments in map_kernel(). We
would allow sections and/or CONT entires.
Then, in __map_memblock() we'd then skip that range as we do for the
linear map alias of the kernel image.
That way, we can later use create_mapping_late for that same region, and
it should handle sections and/or CONT entries in the exact same way as
it does for the kernel image segments in mark_rodata_ro().
> 2) The control code page, of one-page size, is still written out in
> machine_kexec() which is called at a crash, and this means that
> the range must be writable even after kexec_load(), but
> create_mapping_late() does not handle a case of changing attributes
> for a single page which is in _section_ mapping.
> We cannot make single-page mapping for the control page since the address
> of that page is not determined at the boot time.
That is a problem. I'm not sure I follow how set_memory_*() helps here
though?
> As for (1), we need to call memblock_isolate_range() to make the region
> an independent one.
>
> > Either way, this still leaves us with an RO alias on crashed cores (and
> > potential cache attribute mismatches in future). Do we need to read from
> > the region later,
>
> I believe not, but the region must be _writable_ as I mentioned in (2) above.
> To avoid this issue, we have to move copying the control code page
> to machine_kexec_prepare() which is called in kexec_load() and so
> the region is writable anyway then.
> I want Geoff to affirm that this change is safe.
>
> (See my second solution below.)
>From a quick scan that looks ok.
> > or could we unmap it entirely?
>
> given the change above, I think we can.
Great!
> Is there any code to re-use especially for unmapping?
I don't think we have much code useful for unmapping. We could re-use
create_mapping_late for this, passing a set of prot bits that means the
entries are invalid (e.g. have a PAGE_KERNEL_INVALID).
We'd have to perform the TLB invalidation ourselves, but that shouldn't
be too painful.
Thanks,
Mark.
> ===8<===
> diff --git a/arch/arm64/kernel/machine_kexec.c b/arch/arm64/kernel/machine_kexec.c
> index c0fc3d458195..80a52e9aaf73 100644
> --- a/arch/arm64/kernel/machine_kexec.c
> +++ b/arch/arm64/kernel/machine_kexec.c
> @@ -26,8 +26,6 @@
> extern const unsigned char arm64_relocate_new_kernel[];
> extern const unsigned long arm64_relocate_new_kernel_size;
>
> -static unsigned long kimage_start;
> -
> /**
> * kexec_image_info - For debugging output.
> */
> @@ -68,7 +66,7 @@ void machine_kexec_cleanup(struct kimage *kimage)
> */
> int machine_kexec_prepare(struct kimage *kimage)
> {
> - kimage_start = kimage->start;
> + void *reboot_code_buffer;
>
> kexec_image_info(kimage);
>
> @@ -77,6 +75,21 @@ int machine_kexec_prepare(struct kimage *kimage)
> return -EBUSY;
> }
>
> + reboot_code_buffer =
> + phys_to_virt(page_to_phys(kimage->control_code_page));
> +
> + /*
> + * Copy arm64_relocate_new_kernel to the reboot_code_buffer for use
> + * after the kernel is shut down.
> + */
> + memcpy(reboot_code_buffer, arm64_relocate_new_kernel,
> + arm64_relocate_new_kernel_size);
> +
> + /* Flush the reboot_code_buffer in preparation for its execution. */
> + __flush_dcache_area(reboot_code_buffer, arm64_relocate_new_kernel_size);
> + flush_icache_range((uintptr_t)reboot_code_buffer,
> + arm64_relocate_new_kernel_size);
> +
> return 0;
> }
>
> @@ -147,7 +160,6 @@ static void kexec_segment_flush(const struct kimage *kimage)
> void machine_kexec(struct kimage *kimage)
> {
> phys_addr_t reboot_code_buffer_phys;
> - void *reboot_code_buffer;
>
> /*
> * New cpus may have become stuck_in_kernel after we loaded the image.
> @@ -156,7 +168,6 @@ void machine_kexec(struct kimage *kimage)
> !WARN_ON(kimage == kexec_crash_image));
>
> reboot_code_buffer_phys = page_to_phys(kimage->control_code_page);
> - reboot_code_buffer = phys_to_virt(reboot_code_buffer_phys);
>
> kexec_image_info(kimage);
>
> @@ -164,26 +175,12 @@ void machine_kexec(struct kimage *kimage)
> kimage->control_code_page);
> pr_debug("%s:%d: reboot_code_buffer_phys: %pa\n", __func__, __LINE__,
> &reboot_code_buffer_phys);
> - pr_debug("%s:%d: reboot_code_buffer: %p\n", __func__, __LINE__,
> - reboot_code_buffer);
> pr_debug("%s:%d: relocate_new_kernel: %p\n", __func__, __LINE__,
> arm64_relocate_new_kernel);
> pr_debug("%s:%d: relocate_new_kernel_size: 0x%lx(%lu) bytes\n",
> __func__, __LINE__, arm64_relocate_new_kernel_size,
> arm64_relocate_new_kernel_size);
>
> - /*
> - * Copy arm64_relocate_new_kernel to the reboot_code_buffer for use
> - * after the kernel is shut down.
> - */
> - memcpy(reboot_code_buffer, arm64_relocate_new_kernel,
> - arm64_relocate_new_kernel_size);
> -
> - /* Flush the reboot_code_buffer in preparation for its execution. */
> - __flush_dcache_area(reboot_code_buffer, arm64_relocate_new_kernel_size);
> - flush_icache_range((uintptr_t)reboot_code_buffer,
> - arm64_relocate_new_kernel_size);
> -
> /* Flush the kimage list and its buffers. */
> kexec_list_flush(kimage);
>
> @@ -206,7 +203,7 @@ void machine_kexec(struct kimage *kimage)
> */
>
> cpu_soft_restart(kimage != kexec_crash_image,
> - reboot_code_buffer_phys, kimage->head, kimage_start, 0);
> + reboot_code_buffer_phys, kimage->head, kimage->start, 0);
>
> BUG(); /* Should never get here. */
> }
> diff --git a/arch/arm64/mm/init.c b/arch/arm64/mm/init.c
> index 569ec3325bc8..e4cc170edc0c 100644
> --- a/arch/arm64/mm/init.c
> +++ b/arch/arm64/mm/init.c
> @@ -90,6 +90,7 @@ early_param("initrd", early_initrd);
> static void __init reserve_crashkernel(void)
> {
> unsigned long long crash_size, crash_base;
> + int start_rgn, end_rgn;
> int ret;
>
> ret = parse_crashkernel(boot_command_line, memblock_phys_mem_size(),
> @@ -120,6 +121,8 @@ static void __init reserve_crashkernel(void)
> return;
> }
> }
> + memblock_isolate_range(&memblock.memory, crash_base, crash_size,
> + &start_rgn, &end_rgn);
> memblock_reserve(crash_base, crash_size);
>
> pr_info("Reserving %lldMB of memory at %lldMB for crashkernel\n",
> diff --git a/arch/arm64/mm/mmu.c b/arch/arm64/mm/mmu.c
> index 17243e43184e..b7c75845407a 100644
> --- a/arch/arm64/mm/mmu.c
> +++ b/arch/arm64/mm/mmu.c
> @@ -22,6 +22,8 @@
> #include <linux/kernel.h>
> #include <linux/errno.h>
> #include <linux/init.h>
> +#include <linux/ioport.h>
> +#include <linux/kexec.h>
> #include <linux/libfdt.h>
> #include <linux/mman.h>
> #include <linux/nodemask.h>
> @@ -817,3 +819,27 @@ int pmd_clear_huge(pmd_t *pmd)
> pmd_clear(pmd);
> return 1;
> }
> +
> +#ifdef CONFIG_KEXEC_CORE
> +void arch_kexec_protect_crashkres(void)
> +{
> + flush_tlb_all();
> +
> + create_mapping_late(crashk_res.start, __phys_to_virt(crashk_res.start),
> + resource_size(&crashk_res), PAGE_KERNEL_RO);
> +
> + /* flush the TLBs after updating live kernel mappings */
> + flush_tlb_all();
> +}
> +
> +void arch_kexec_unprotect_crashkres(void)
> +{
> + flush_tlb_all();
> +
> + create_mapping_late(crashk_res.start, __phys_to_virt(crashk_res.start),
> + resource_size(&crashk_res), PAGE_KERNEL);
> +
> + /* flush the TLBs after updating live kernel mappings */
> + flush_tlb_all();
> +}
> +#endif
> ===>8===
^ permalink raw reply
* [PATCH v8 01/18] iommu/dma: Allow MSI-only cookies
From: Tomasz Nowicki @ 2017-01-17 11:59 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484127714-3263-2-git-send-email-eric.auger@redhat.com>
On 11.01.2017 10:41, Eric Auger wrote:
> From: Robin Murphy <robin.murphy@arm.com>
>
> IOMMU domain users such as VFIO face a similar problem to DMA API ops
> with regard to mapping MSI messages in systems where the MSI write is
> subject to IOMMU translation. With the relevant infrastructure now in
> place for managed DMA domains, it's actually really simple for other
> users to piggyback off that and reap the benefits without giving up
> their own IOVA management, and without having to reinvent their own
> wheel in the MSI layer.
>
> Allow such users to opt into automatic MSI remapping by dedicating a
> region of their IOVA space to a managed cookie, and extend the mapping
> routine to implement a trivial linear allocator in such cases, to avoid
> the needless overhead of a full-blown IOVA domain.
>
> Signed-off-by: Robin Murphy <robin.murphy@arm.com>
Reviewed-by: Tomasz Nowicki <tomasz.nowicki@caviumnetworks.com>
Thanks,
Tomasz
> ---
> drivers/iommu/dma-iommu.c | 119 +++++++++++++++++++++++++++++++++++++---------
> include/linux/dma-iommu.h | 6 +++
> 2 files changed, 102 insertions(+), 23 deletions(-)
>
> diff --git a/drivers/iommu/dma-iommu.c b/drivers/iommu/dma-iommu.c
> index 2db0d64..de41ead 100644
> --- a/drivers/iommu/dma-iommu.c
> +++ b/drivers/iommu/dma-iommu.c
> @@ -37,15 +37,50 @@ struct iommu_dma_msi_page {
> phys_addr_t phys;
> };
>
> +enum iommu_dma_cookie_type {
> + IOMMU_DMA_IOVA_COOKIE,
> + IOMMU_DMA_MSI_COOKIE,
> +};
> +
> struct iommu_dma_cookie {
> - struct iova_domain iovad;
> - struct list_head msi_page_list;
> - spinlock_t msi_lock;
> + enum iommu_dma_cookie_type type;
> + union {
> + /* Full allocator for IOMMU_DMA_IOVA_COOKIE */
> + struct iova_domain iovad;
> + /* Trivial linear page allocator for IOMMU_DMA_MSI_COOKIE */
> + dma_addr_t msi_iova;
> + };
> + struct list_head msi_page_list;
> + spinlock_t msi_lock;
> };
>
> +static inline size_t cookie_msi_granule(struct iommu_dma_cookie *cookie)
> +{
> + if (cookie->type == IOMMU_DMA_IOVA_COOKIE)
> + return cookie->iovad.granule;
> + return PAGE_SIZE;
> +}
> +
> static inline struct iova_domain *cookie_iovad(struct iommu_domain *domain)
> {
> - return &((struct iommu_dma_cookie *)domain->iova_cookie)->iovad;
> + struct iommu_dma_cookie *cookie = domain->iova_cookie;
> +
> + if (cookie->type == IOMMU_DMA_IOVA_COOKIE)
> + return &cookie->iovad;
> + return NULL;
> +}
> +
> +static struct iommu_dma_cookie *cookie_alloc(enum iommu_dma_cookie_type type)
> +{
> + struct iommu_dma_cookie *cookie;
> +
> + cookie = kzalloc(sizeof(*cookie), GFP_KERNEL);
> + if (cookie) {
> + spin_lock_init(&cookie->msi_lock);
> + INIT_LIST_HEAD(&cookie->msi_page_list);
> + cookie->type = type;
> + }
> + return cookie;
> }
>
> int iommu_dma_init(void)
> @@ -62,25 +97,53 @@ int iommu_dma_init(void)
> */
> int iommu_get_dma_cookie(struct iommu_domain *domain)
> {
> + if (domain->iova_cookie)
> + return -EEXIST;
> +
> + domain->iova_cookie = cookie_alloc(IOMMU_DMA_IOVA_COOKIE);
> + if (!domain->iova_cookie)
> + return -ENOMEM;
> +
> + return 0;
> +}
> +EXPORT_SYMBOL(iommu_get_dma_cookie);
> +
> +/**
> + * iommu_get_msi_cookie - Acquire just MSI remapping resources
> + * @domain: IOMMU domain to prepare
> + * @base: Start address of IOVA region for MSI mappings
> + *
> + * Users who manage their own IOVA allocation and do not want DMA API support,
> + * but would still like to take advantage of automatic MSI remapping, can use
> + * this to initialise their own domain appropriately. Users should reserve a
> + * contiguous IOVA region, starting at @base, large enough to accommodate the
> + * number of PAGE_SIZE mappings necessary to cover every MSI doorbell address
> + * used by the devices attached to @domain.
> + */
> +int iommu_get_msi_cookie(struct iommu_domain *domain, dma_addr_t base)
> +{
> struct iommu_dma_cookie *cookie;
>
> + if (domain->type != IOMMU_DOMAIN_UNMANAGED)
> + return -EINVAL;
> +
> if (domain->iova_cookie)
> return -EEXIST;
>
> - cookie = kzalloc(sizeof(*cookie), GFP_KERNEL);
> + cookie = cookie_alloc(IOMMU_DMA_MSI_COOKIE);
> if (!cookie)
> return -ENOMEM;
>
> - spin_lock_init(&cookie->msi_lock);
> - INIT_LIST_HEAD(&cookie->msi_page_list);
> + cookie->msi_iova = base;
> domain->iova_cookie = cookie;
> return 0;
> }
> -EXPORT_SYMBOL(iommu_get_dma_cookie);
> +EXPORT_SYMBOL(iommu_get_msi_cookie);
>
> /**
> * iommu_put_dma_cookie - Release a domain's DMA mapping resources
> - * @domain: IOMMU domain previously prepared by iommu_get_dma_cookie()
> + * @domain: IOMMU domain previously prepared by iommu_get_dma_cookie() or
> + * iommu_get_msi_cookie()
> *
> * IOMMU drivers should normally call this from their domain_free callback.
> */
> @@ -92,7 +155,7 @@ void iommu_put_dma_cookie(struct iommu_domain *domain)
> if (!cookie)
> return;
>
> - if (cookie->iovad.granule)
> + if (cookie->type == IOMMU_DMA_IOVA_COOKIE && cookie->iovad.granule)
> put_iova_domain(&cookie->iovad);
>
> list_for_each_entry_safe(msi, tmp, &cookie->msi_page_list, list) {
> @@ -137,11 +200,12 @@ static void iova_reserve_pci_windows(struct pci_dev *dev,
> int iommu_dma_init_domain(struct iommu_domain *domain, dma_addr_t base,
> u64 size, struct device *dev)
> {
> - struct iova_domain *iovad = cookie_iovad(domain);
> + struct iommu_dma_cookie *cookie = domain->iova_cookie;
> + struct iova_domain *iovad = &cookie->iovad;
> unsigned long order, base_pfn, end_pfn;
>
> - if (!iovad)
> - return -ENODEV;
> + if (!cookie || cookie->type != IOMMU_DMA_IOVA_COOKIE)
> + return -EINVAL;
>
> /* Use the smallest supported page size for IOVA granularity */
> order = __ffs(domain->pgsize_bitmap);
> @@ -662,11 +726,12 @@ static struct iommu_dma_msi_page *iommu_dma_get_msi_page(struct device *dev,
> {
> struct iommu_dma_cookie *cookie = domain->iova_cookie;
> struct iommu_dma_msi_page *msi_page;
> - struct iova_domain *iovad = &cookie->iovad;
> + struct iova_domain *iovad = cookie_iovad(domain);
> struct iova *iova;
> int prot = IOMMU_WRITE | IOMMU_NOEXEC | IOMMU_MMIO;
> + size_t size = cookie_msi_granule(cookie);
>
> - msi_addr &= ~(phys_addr_t)iova_mask(iovad);
> + msi_addr &= ~(phys_addr_t)(size - 1);
> list_for_each_entry(msi_page, &cookie->msi_page_list, list)
> if (msi_page->phys == msi_addr)
> return msi_page;
> @@ -675,13 +740,18 @@ static struct iommu_dma_msi_page *iommu_dma_get_msi_page(struct device *dev,
> if (!msi_page)
> return NULL;
>
> - iova = __alloc_iova(domain, iovad->granule, dma_get_mask(dev));
> - if (!iova)
> - goto out_free_page;
> -
> msi_page->phys = msi_addr;
> - msi_page->iova = iova_dma_addr(iovad, iova);
> - if (iommu_map(domain, msi_page->iova, msi_addr, iovad->granule, prot))
> + if (iovad) {
> + iova = __alloc_iova(domain, size, dma_get_mask(dev));
> + if (!iova)
> + goto out_free_page;
> + msi_page->iova = iova_dma_addr(iovad, iova);
> + } else {
> + msi_page->iova = cookie->msi_iova;
> + cookie->msi_iova += size;
> + }
> +
> + if (iommu_map(domain, msi_page->iova, msi_addr, size, prot))
> goto out_free_iova;
>
> INIT_LIST_HEAD(&msi_page->list);
> @@ -689,7 +759,10 @@ static struct iommu_dma_msi_page *iommu_dma_get_msi_page(struct device *dev,
> return msi_page;
>
> out_free_iova:
> - __free_iova(iovad, iova);
> + if (iovad)
> + __free_iova(iovad, iova);
> + else
> + cookie->msi_iova -= size;
> out_free_page:
> kfree(msi_page);
> return NULL;
> @@ -730,7 +803,7 @@ void iommu_dma_map_msi_msg(int irq, struct msi_msg *msg)
> msg->data = ~0U;
> } else {
> msg->address_hi = upper_32_bits(msi_page->iova);
> - msg->address_lo &= iova_mask(&cookie->iovad);
> + msg->address_lo &= cookie_msi_granule(cookie) - 1;
> msg->address_lo += lower_32_bits(msi_page->iova);
> }
> }
> diff --git a/include/linux/dma-iommu.h b/include/linux/dma-iommu.h
> index 7f7e9a7..28df844 100644
> --- a/include/linux/dma-iommu.h
> +++ b/include/linux/dma-iommu.h
> @@ -27,6 +27,7 @@
>
> /* Domain management interface for IOMMU drivers */
> int iommu_get_dma_cookie(struct iommu_domain *domain);
> +int iommu_get_msi_cookie(struct iommu_domain *domain, dma_addr_t base);
> void iommu_put_dma_cookie(struct iommu_domain *domain);
>
> /* Setup call for arch DMA mapping code */
> @@ -86,6 +87,11 @@ static inline int iommu_get_dma_cookie(struct iommu_domain *domain)
> return -ENODEV;
> }
>
> +static inline int iommu_get_msi_cookie(struct iommu_domain *domain, dma_addr_t base)
> +{
> + return -ENODEV;
> +}
> +
> static inline void iommu_put_dma_cookie(struct iommu_domain *domain)
> {
> }
>
^ permalink raw reply
* [PATCH v7 15/15] irqchip: mbigen: Add ACPI support
From: Hanjun Guo @ 2017-01-17 11:59 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20170116152413.GA24135@red-moon>
On 2017/1/16 23:24, Lorenzo Pieralisi wrote:
> On Mon, Jan 16, 2017 at 10:23:16PM +0800, Hanjun Guo wrote:
>> Hi Lorenzo,
>>
>> On 2017/1/16 19:38, Lorenzo Pieralisi wrote:
>>> On Sat, Jan 14, 2017 at 10:56:54AM +0800, Hanjun Guo wrote:
>>>> Hi Lorenzo,
>>>>
>>>> On 2017/1/13 18:21, Lorenzo Pieralisi wrote:
>>>>> On Wed, Jan 11, 2017 at 11:06:39PM +0800, Hanjun Guo wrote:
>>>>>> With the preparation of platform msi support and interrupt producer
>>>>>> in DSDT, we can add mbigen ACPI support now.
>>>>>>
>>>>>> We are using _PRS methd to indicate number of irq pins instead
>>>>>> of num_pins in DT to avoid _DSD usage in this case.
>>>>>>
>>>>>> For mbi-gen,
>>>>>> Device(MBI0) {
>>>>>> Name(_HID, "HISI0152")
>>>>>> Name(_UID, Zero)
>>>>>> Name(_CRS, ResourceTemplate() {
>>>>>> Memory32Fixed(ReadWrite, 0xa0080000, 0x10000)
>>>>>> })
>>>>>>
>>>>>> Name (_PRS, ResourceTemplate() {
>>>>>> Interrupt(ResourceProducer,...) {12,14,....}
>>>>> I still do not understand why you are using _PRS for this, I think
>>>>> the MBIgen configuration is static and if it is so the Interrupt
>>>>> resource should be part of the _CRS unless there is something I am
>>>>> missing here.
>>>> Sorry for not clear in the commit message. MBIgen is an interrupt producer
>>>> which produces irq resource to devices connecting to it, and MBIgen itself
>>>> don't consume wired interrupts.
>>> That's why you mark it as ResourceProducer, but that's not a reason to
>>> put it in the _PRS instead of _CRS.
>> If using _CRS for the interrupt resource, the irq number represented
>> will be mapped (i.e acpi_register_gsi()), then will conflict with the
>> irq number of devices consuming it (mbigen is producing the
>> interrupts), but I agree with you that let's ask Rafael's point of
>> view.
> Aha ! So here is why you are using _PRS because the kernel turns _CRS
> Interrupt resources (even producers) into GSIs which is probably a
> kernel bug, is that the reason ?
I thought _CRS is for devices consuming resources, it's a kind of misunderstanding.
>
> We don't abuse firmware bindings to make the kernel work, that's _never_
> a good idea.
>
> If the interrupt resource is a Resource Producer core ACPI should not
> register the IRQ because that's not a GSI, probably this should be part of
> Agustin changes too ?
Agreed. If it's a Resource Producer,
- it's not a GSI
- and it should not be mapped to any irq domains
I think Agustin needs to add the changes to the patch set but only for
CONFIG_ACPI_GENERIC_GSI=y, not bother the core code as the complex
history of firmware in x86, what do you think?
>
>>> IIUC _PRS is there to provide a way to define the possible resource
>>> settings of a _configurable_ device (ie programmable) so that the actual
>>> resource value you would programme with a call to its _SRS is sane (ie
>>> the OS has a way, through the _PRS, to detect what possible resource
>>> settings are available for the device).
>>>
>>> I think Rafael has more insights into how the _PRS is used on x86
>>> systems so I would ask his point of view here before merrily merging
>>> this code.
>> OK, Rafael is traveling now, hope he will have time to take a look.
>>
>> How about updating this patch set then sending a new version for review
>> with this patch unchanged? if Rafael have comments on this one, I will
>> send a single updated one for this patch (if no other changes).
> I think this patch (and the FW that goes with it) is wrong, but the rest
> of the series, in particular the IORT bits, are ok with me.
Thanks, I updated the patch using _CRS and firmware, with minor changes for
Agustin's patch set, mbigen works pretty good as before.
I will comment on Agustin's patch set.
Thanks
Hanjun
^ permalink raw reply
* [PATCH 03/10] devicetree: bindings: add bindings for ahci-da850
From: Sekhar Nori @ 2017-01-17 12:00 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <fb93275e-73ad-513b-6ac8-a39bbe43fd5c@lechnology.com>
On Tuesday 17 January 2017 12:17 AM, David Lechner wrote:
> On 01/16/2017 08:30 AM, Bartosz Golaszewski wrote:
>> 2017-01-16 13:45 GMT+01:00 Sekhar Nori <nsekhar@ti.com>:
>>> On Monday 16 January 2017 03:43 PM, Bartosz Golaszewski wrote:
>>>> 2017-01-13 20:25 GMT+01:00 David Lechner <david@lechnology.com>:
>>>>>
>>>>> A clock multiplier property seems redundant if you are specifying a
>>>>> clock.
>>>>> It should be possible to get the rate from the clock to determine
>>>>> which
>>>>> multiplier is needed.
>>>>>
>>>>
>>>> I probably should have named it differently. This is not a multiplier
>>>> of a clock derived from PLL0 or PLL1. Instead it's a value set by
>>>> writing to the Port PHY Control Register (MPY bits) of the SATA
>>>> controller that configures the multiplier for the external low-jitter
>>>> clock. On the lcdk the signals (REFCLKP, REFCLKN) are provided by
>>>> CDCM61001 (SATA OSCILLATOR component on the schematics).
>>>>
>>>> I'll find a better name and comment the property accordingly.
>>>>
>>>> FYI: the da850 platform does not use the common clock framework, so I
>>>> don't specify the clock property on the sata node in the device tree.
>>>> Instead I add the clock lookup entry in patch [01/10]. This is
>>>> transparent for AHCI which can get the clock as usual by calling
>>>> clk_get() in ahci_platform_get_resources().
>>>
>>> I think David's point is that the SATA_REFCLK needs to be modeled as a
>>> actual clock input to the IP. You should be able to get the rate using
>>> clk_get_rate() and make the MPY bits calculation depending on the
>>> incoming rate.
>>>
>>> You should be able to model the clock even when not using common clock
>>> framework.
>>>
>>> DA850 AHCI does not use a con_id at the moment (it assumes a single
>>> clock), and that needs to change.
>>>
>>
>> It's true that once davinci gets ported (is this planned?) to using
>> the common clock framework, we could just create a fixed-clock node in
>> da850-lcdk for the SATA oscillator, so the new property is redundant.
>>
>
> I have some commits[1] where I started on converting da850 to use the
> common clock framework. But, I don't know anything about other davinci
> family devices, so I don't think I could really take that to completion
> without lots of help.
I can help with testing, reviewing and filling in any missing
information. But I wont have time to write the code itself.
>
> [1]: https://github.com/dlech/ev3dev-kernel/commits/wip-20160509
I see that you have made a copy of the keystone PSC driver. I think you
will need pretty strong reasons to not use the same driver with some
customization for DaVinci.
>> What I don't get is how should I model a clock that is not
>> configurable and is board-specific? Is hard-coding the relevant rate
>> in da850.c with a huge FIXME the right way?
>
> In arch/arm/mach-davinci/usb-da8xx.c, there is a "usb_refclkin" that is
> very similar to the situation with the sata refclk. You could do
> something like this to register the clock...
>
> ---
>
> diff --git a/arch/arm/mach-davinci/devices-da8xx.c
> b/arch/arm/mach-davinci/devices-da8xx.c
> index c2457b3..790efce9 100644
> --- a/arch/arm/mach-davinci/devices-da8xx.c
> +++ b/arch/arm/mach-davinci/devices-da8xx.c
> @@ -1023,6 +1023,34 @@ int __init da8xx_register_spi_bus(int instance,
> unsigned num_chipselect)
> }
>
> #ifdef CONFIG_ARCH_DAVINCI_DA850
> +
> +static struct clk sata_refclkin = {
> + .name = "sata_refclkin",
> + .set_rate = davinci_simple_set_rate,
> +};
> +
> +static struct clk_lookup sata_refclkin_lookup =
> + CLK(NULL, "sata_refclkin", &sata_refclkin);
> +
> +/**
> + * da8xx_register_sata_refclkin - register SATA_REFCLKIN clock
> + *
> + * @rate: The clock rate in Hz
> + */
> +int __init da850_register_sata_refclkin(int rate)
> +{
> + int ret;
> +
> + sata_refclkin.rate = rate;
> + ret = clk_register(&sata_refclkin);
> + if (ret)
> + return ret;
> +
> + clkdev_add(&sata_refclkin_lookup);
> +
> + return 0;
> +}
> +
> static struct resource da850_sata_resources[] = {
> {
> .start = DA850_SATA_BASE,
> @@ -1055,8 +1083,11 @@ static struct platform_device da850_sata_device = {
>
> int __init da850_register_sata(unsigned long refclkpn)
> {
> - /* please see comment in drivers/ata/ahci_da850.c */
> - BUG_ON(refclkpn != 100 * 1000 * 1000);
> + int err;
> +
> + err = da850_register_sata_refclkin(refclkpn);
> + if (err)
> + return err;
>
> return platform_device_register(&da850_sata_device);
> }
>
> ---
>
> Then to get things working from device tree, add this...
>
> ---
>
> diff --git a/arch/arm/mach-davinci/da8xx-dt.c
> b/arch/arm/mach-davinci/da8xx-dt.c
> index d2be194..b54bdd6 100644
> --- a/arch/arm/mach-davinci/da8xx-dt.c
> +++ b/arch/arm/mach-davinci/da8xx-dt.c
> @@ -60,6 +60,14 @@ static void __init da850_init_machine(void)
> pr_warn("%s: registering USB 1.1 PHY clock failed: %d",
> __func__, ret);
>
> + if (of_machine_is_compatible("ti,da850-evm") ||
> + of_machine_is_compatible("ti,da850-lcdk")) {
> + ret = da850_register_sata_refclkin(100000000);
> + if (ret)
> + pr_warn("%s: registering SATA_REFCLK clock
> failed: %d",
> + __func__, ret);
> + }
> +
> of_platform_default_populate(NULL, da850_auxdata_lookup, NULL);
> davinci_pm_init();
> pdata_quirks_init();
This approach is fine.
Thanks,
Sekhar
^ permalink raw reply
* [Question] A question about arm64 pte
From: Yisheng Xie @ 2017-01-17 12:02 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20170117114518.GF18923@e104818-lin.cambridge.arm.com>
On 2017/1/17 19:45, Catalin Marinas wrote:
> On Tue, Jan 17, 2017 at 11:53:43AM +0800, Yisheng Xie wrote:
>> On 2017/1/16 22:36, Catalin Marinas wrote:
>>> On Mon, Jan 16, 2017 at 08:39:56PM +0800, Yisheng Xie wrote:
>>>> On 2017/1/16 19:56, Catalin Marinas wrote:
>>>>> On Mon, Jan 16, 2017 at 06:08:47PM +0800, Yisheng Xie wrote:
>>>>>
>>
>> Here is what I get when mmap a reserved memory region 0x39ef 0000~0x3a00 0000
>> use /dev/mem:
>> [ 442.704228] pgd = ffff802785f14000
>> [ 442.707641] [ffff86e4b000] *pgd=000000279080c003, *pud=0000002785f01003, *pmd=0000002783f5b003, *pte=0168000039ef0fd3
>
> The pte seems to have bit 7 set: PTE_RDONLY. So you would get a fault on
> write (but not read). Since PTE_WRITE is also set, handle_pte_fault()
> will mark the entry as dirty (bit 55, cleared above) and clear
> PTE_RDONLY before restarting the access instruction. User space wouldn't
> notice, just a slight delay on the first access.
>
Hi Catalin,
Really thank you for kindly explain, quite clear now.
Thanks
Yisheng Xie.
^ permalink raw reply
* [PATCH 0/2] pinctrl: meson-gx: Add HDMI HDP/DDC pins functions
From: Neil Armstrong @ 2017-01-17 12:05 UTC (permalink / raw)
To: linux-arm-kernel
In order to support HDMI HPD and DDC, add missing functions in pinctrl
driver and add corresponding nodes in dts for GXBB and GXL.
Neil Armstrong (2):
pinctrl: meson: Add HDMI HPD/DDC pins functions
ARM64: dts: meson-gx: Add HDMI HPD/DDC pinctrl nodes
arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 14 ++++++++++++++
arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 14 ++++++++++++++
drivers/pinctrl/meson/pinctrl-meson-gxbb.c | 19 +++++++++++++++++++
drivers/pinctrl/meson/pinctrl-meson-gxl.c | 19 +++++++++++++++++++
4 files changed, 66 insertions(+)
--
1.9.1
^ permalink raw reply
* [PATCH 1/2] pinctrl: meson: Add HDMI HPD/DDC pins functions
From: Neil Armstrong @ 2017-01-17 12:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484654738-5496-1-git-send-email-narmstrong@baylibre.com>
Add pinctrl functions for HDMI HPD pin and DDC pins on Amlogic Meson
GXL and GXBB SoCs.
Signed-off-by: Neil Armstrong <narmstrong@baylibre.com>
---
drivers/pinctrl/meson/pinctrl-meson-gxbb.c | 19 +++++++++++++++++++
drivers/pinctrl/meson/pinctrl-meson-gxl.c | 19 +++++++++++++++++++
2 files changed, 38 insertions(+)
diff --git a/drivers/pinctrl/meson/pinctrl-meson-gxbb.c b/drivers/pinctrl/meson/pinctrl-meson-gxbb.c
index c3928aa..0d9ad36 100644
--- a/drivers/pinctrl/meson/pinctrl-meson-gxbb.c
+++ b/drivers/pinctrl/meson/pinctrl-meson-gxbb.c
@@ -232,6 +232,10 @@
static const unsigned int pwm_f_x_pins[] = { PIN(GPIOX_7, EE_OFF) };
static const unsigned int pwm_f_y_pins[] = { PIN(GPIOY_15, EE_OFF) };
+static const unsigned int hdmi_hpd_pins[] = { PIN(GPIOH_0, EE_OFF) };
+static const unsigned int hdmi_sda_pins[] = { PIN(GPIOH_1, EE_OFF) };
+static const unsigned int hdmi_scl_pins[] = { PIN(GPIOH_2, EE_OFF) };
+
static const struct pinctrl_pin_desc meson_gxbb_aobus_pins[] = {
MESON_PIN(GPIOAO_0, 0),
MESON_PIN(GPIOAO_1, 0),
@@ -440,6 +444,11 @@
GROUP(eth_txd2, 6, 3),
GROUP(eth_txd3, 6, 2),
+ /* Bank H */
+ GROUP(hdmi_hpd, 1, 26),
+ GROUP(hdmi_sda, 1, 25),
+ GROUP(hdmi_scl, 1, 24),
+
/* Bank DV */
GROUP(uart_tx_b, 2, 29),
GROUP(uart_rx_b, 2, 28),
@@ -636,6 +645,14 @@
"pwm_f_y",
};
+static const char * const hdmi_hpd_groups[] = {
+ "hdmi_hpd",
+};
+
+static const char * const hdmi_i2c_groups[] = {
+ "hdmi_sda", "hdmi_scl",
+};
+
static const char * const gpio_aobus_groups[] = {
"GPIOAO_0", "GPIOAO_1", "GPIOAO_2", "GPIOAO_3", "GPIOAO_4",
"GPIOAO_5", "GPIOAO_6", "GPIOAO_7", "GPIOAO_8", "GPIOAO_9",
@@ -699,6 +716,8 @@
FUNCTION(pwm_e),
FUNCTION(pwm_f_x),
FUNCTION(pwm_f_y),
+ FUNCTION(hdmi_hpd),
+ FUNCTION(hdmi_i2c),
};
static struct meson_pmx_func meson_gxbb_aobus_functions[] = {
diff --git a/drivers/pinctrl/meson/pinctrl-meson-gxl.c b/drivers/pinctrl/meson/pinctrl-meson-gxl.c
index 25694f7..7703a46 100644
--- a/drivers/pinctrl/meson/pinctrl-meson-gxl.c
+++ b/drivers/pinctrl/meson/pinctrl-meson-gxl.c
@@ -197,6 +197,10 @@
static const unsigned int pwm_e_pins[] = { PIN(GPIOX_16, EE_OFF) };
+static const unsigned int hdmi_hpd_pins[] = { PIN(GPIOH_0, EE_OFF) };
+static const unsigned int hdmi_sda_pins[] = { PIN(GPIOH_1, EE_OFF) };
+static const unsigned int hdmi_scl_pins[] = { PIN(GPIOH_2, EE_OFF) };
+
static const struct pinctrl_pin_desc meson_gxl_aobus_pins[] = {
MESON_PIN(GPIOAO_0, 0),
MESON_PIN(GPIOAO_1, 0),
@@ -363,6 +367,11 @@
GROUP(eth_txd2, 4, 11),
GROUP(eth_txd3, 4, 10),
+ /* Bank H */
+ GROUP(hdmi_hpd, 6, 31),
+ GROUP(hdmi_sda, 6, 30),
+ GROUP(hdmi_scl, 6, 29),
+
/* Bank DV */
GROUP(uart_tx_b, 2, 16),
GROUP(uart_rx_b, 2, 15),
@@ -506,6 +515,14 @@
"pwm_e",
};
+static const char * const hdmi_hpd_groups[] = {
+ "hdmi_hpd",
+};
+
+static const char * const hdmi_i2c_groups[] = {
+ "hdmi_sda", "hdmi_scl",
+};
+
static const char * const gpio_aobus_groups[] = {
"GPIOAO_0", "GPIOAO_1", "GPIOAO_2", "GPIOAO_3", "GPIOAO_4",
"GPIOAO_5", "GPIOAO_6", "GPIOAO_7", "GPIOAO_8", "GPIOAO_9",
@@ -537,6 +554,8 @@
FUNCTION(i2c_c),
FUNCTION(eth),
FUNCTION(pwm_e),
+ FUNCTION(hdmi_hpd),
+ FUNCTION(hdmi_i2c),
};
static struct meson_pmx_func meson_gxl_aobus_functions[] = {
--
1.9.1
^ permalink raw reply related
* [PATCH 2/2] ARM64: dts: meson-gx: Add HDMI HPD/DDC pinctrl nodes
From: Neil Armstrong @ 2017-01-17 12:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484654738-5496-1-git-send-email-narmstrong@baylibre.com>
Add pinctrl nodes for HDMI HPD and DDC pins modes for Amlogic Meson GXL
and GXBB SoCs.
Signed-off-by: Neil Armstrong <narmstrong@baylibre.com>
---
arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 14 ++++++++++++++
arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 14 ++++++++++++++
2 files changed, 28 insertions(+)
diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi
index 596240c..31d64a1 100644
--- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi
+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi
@@ -463,6 +463,20 @@
function = "pwm_f_y";
};
};
+
+ hdmi_hpd_pins: hdmi_hpd {
+ mux {
+ groups = "hdmi_hpd";
+ function = "hdmi_hpd";
+ };
+ };
+
+ hdmi_i2c_pins: hdmi_i2c {
+ mux {
+ groups = "hdmi_sda", "hdmi_scl";
+ function = "hdmi_i2c";
+ };
+ };
};
};
diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi
index 6921624..17dbcf6 100644
--- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi
+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi
@@ -229,6 +229,20 @@
function = "pwm_e";
};
};
+
+ hdmi_hpd_pins: hdmi_hpd {
+ mux {
+ groups = "hdmi_hpd";
+ function = "hdmi_hpd";
+ };
+ };
+
+ hdmi_i2c_pins: hdmi_i2c {
+ mux {
+ groups = "hdmi_sda", "hdmi_scl";
+ function = "hdmi_i2c";
+ };
+ };
};
eth-phy-mux {
--
1.9.1
^ permalink raw reply related
* [arm-platforms:kvm-arm64/gicv4-wip 30/40] drivers/irqchip/irq-gic-v3-its.c:997:3: error: implicit declaration of function 'writeq_relaxed'
From: kbuild test robot @ 2017-01-17 12:07 UTC (permalink / raw)
To: linux-arm-kernel
tree: https://git.kernel.org/pub/scm/linux/kernel/git/maz/arm-platforms.git kvm-arm64/gicv4-wip
head: fed7acd3fb70199b1c28fa230ee4f92ed674dd12
commit: 650b00e0e6193450bc6f4734cfa630f85606aa3f [30/40] irqchip/gic-v3-its: Add VPE interrupt masking
config: arm-multi_v7_defconfig (attached as .config)
compiler: arm-linux-gnueabi-gcc (Debian 6.1.1-9) 6.1.1 20160705
reproduce:
wget https://git.kernel.org/cgit/linux/kernel/git/wfg/lkp-tests.git/plain/sbin/make.cross -O ~/bin/make.cross
chmod +x ~/bin/make.cross
git checkout 650b00e0e6193450bc6f4734cfa630f85606aa3f
# save the attached .config to linux build tree
make.cross ARCH=arm
All errors (new ones prefixed by >>):
drivers/irqchip/irq-gic-v3-its.c: In function 'lpi_update_config':
>> drivers/irqchip/irq-gic-v3-its.c:997:3: error: implicit declaration of function 'writeq_relaxed' [-Werror=implicit-function-declaration]
writeq_relaxed(d->hwirq, rdbase + GICR_INVLPIR);
^~~~~~~~~~~~~~
In file included from include/linux/kernel.h:10:0,
from include/linux/list.h:8,
from include/linux/resource_ext.h:17,
from include/linux/acpi.h:26,
from drivers/irqchip/irq-gic-v3-its.c:18:
drivers/irqchip/irq-gic-v3-its.c: In function 'its_vpe_set_vcpu_affinity':
include/linux/bitops.h:22:27: warning: right shift count is negative [-Wshift-count-negative]
(((~0UL) << (l)) & (~0UL >> (BITS_PER_LONG - 1 - (h))))
^
drivers/irqchip/irq-gic-v3-its.c:2171:54: note: in expansion of macro 'GENMASK'
val = virt_to_phys(page_address(vpe->vpt_page)) & GENMASK(51, 16);
^~~~~~~
cc1: some warnings being treated as errors
vim +/writeq_relaxed +997 drivers/irqchip/irq-gic-v3-its.c
991 its_send_inv(its_dev, its_get_event_id(d));
992 } else {
993 struct its_vpe *vpe = irq_data_get_irq_chip_data(d);
994 void __iomem *rdbase;
995
996 rdbase = per_cpu_ptr(gic_rdists->rdist, vpe->col_idx)->rd_base;
> 997 writeq_relaxed(d->hwirq, rdbase + GICR_INVLPIR);
998 }
999 }
1000
---
0-DAY kernel test infrastructure Open Source Technology Center
https://lists.01.org/pipermail/kbuild-all Intel Corporation
-------------- next part --------------
A non-text attachment was scrubbed...
Name: .config.gz
Type: application/gzip
Size: 39892 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20170117/cc7230c7/attachment-0001.gz>
^ permalink raw reply
* [kvm-unit-tests PATCH 6/6] run_tests: allow passing of options to QEMU
From: Alex Bennée @ 2017-01-17 12:07 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <648638bd-a90e-ee98-337a-223ed533f53a@redhat.com>
Paolo Bonzini <pbonzini@redhat.com> writes:
> On 12/01/2017 18:32, Andrew Jones wrote:
>>>
>>> +# Any options left for QEMU?
>>> +shift $((OPTIND-1))
>>> +if [ "$#" -gt 0 ]; then
>>> + extra_opts="$@"
>>> +fi
>> We can unconditionally do the extra_opts="$@", extra_opts will just
>> be null in the case there aren't more args, like it was before.
>
> extra_opts is not an array, so this would mess up options that contain
> spaces. (Alex's patch in general, not your tweak).
Is it worth treating extra_opts as an array?
>
> Paolo
>
>>> +
>>> RUNTIME_log_stderr () { cat >> test.log; }
>>> RUNTIME_log_stdout () {
>>> if [ "$PRETTY_PRINT_STACKS" = "yes" ]; then
>>> @@ -59,4 +68,4 @@ RUNTIME_log_stdout () {
>>> config=$TEST_DIR/unittests.cfg
>>> rm -f test.log
>>> printf "BUILD_HEAD=$(cat build-head)\n\n" > test.log
>>> -for_each_unittest $config run
>>> +for_each_unittest $config run "$extra_opts"
--
Alex Benn?e
^ permalink raw reply
* [PATCH v8 02/18] iommu: Rename iommu_dm_regions into iommu_resv_regions
From: Tomasz Nowicki @ 2017-01-17 12:08 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484127714-3263-3-git-send-email-eric.auger@redhat.com>
On 11.01.2017 10:41, Eric Auger wrote:
> We want to extend the callbacks used for dm regions and
> use them for reserved regions. Reserved regions can be
> - directly mapped regions
> - regions that cannot be iommu mapped (PCI host bridge windows, ...)
> - MSI regions (because they belong to another address space or because
> they are not translated by the IOMMU and need special handling)
>
> So let's rename the struct and also the callbacks.
>
> Signed-off-by: Eric Auger <eric.auger@redhat.com>
> Acked-by: Robin Murphy <robin.murphy@arm.com>
Reviewed-by: Tomasz Nowicki <tomasz.nowicki@caviumnetworks.com>
Thanks,
Tomasz
>
> ---
>
> v3 -> v4:
> - add Robin's A-b
> ---
> drivers/iommu/amd_iommu.c | 20 ++++++++++----------
> drivers/iommu/iommu.c | 22 +++++++++++-----------
> include/linux/iommu.h | 29 +++++++++++++++--------------
> 3 files changed, 36 insertions(+), 35 deletions(-)
>
> diff --git a/drivers/iommu/amd_iommu.c b/drivers/iommu/amd_iommu.c
> index 3ef0f42..f7a024f 100644
> --- a/drivers/iommu/amd_iommu.c
> +++ b/drivers/iommu/amd_iommu.c
> @@ -3161,8 +3161,8 @@ static bool amd_iommu_capable(enum iommu_cap cap)
> return false;
> }
>
> -static void amd_iommu_get_dm_regions(struct device *dev,
> - struct list_head *head)
> +static void amd_iommu_get_resv_regions(struct device *dev,
> + struct list_head *head)
> {
> struct unity_map_entry *entry;
> int devid;
> @@ -3172,7 +3172,7 @@ static void amd_iommu_get_dm_regions(struct device *dev,
> return;
>
> list_for_each_entry(entry, &amd_iommu_unity_map, list) {
> - struct iommu_dm_region *region;
> + struct iommu_resv_region *region;
>
> if (devid < entry->devid_start || devid > entry->devid_end)
> continue;
> @@ -3195,18 +3195,18 @@ static void amd_iommu_get_dm_regions(struct device *dev,
> }
> }
>
> -static void amd_iommu_put_dm_regions(struct device *dev,
> +static void amd_iommu_put_resv_regions(struct device *dev,
> struct list_head *head)
> {
> - struct iommu_dm_region *entry, *next;
> + struct iommu_resv_region *entry, *next;
>
> list_for_each_entry_safe(entry, next, head, list)
> kfree(entry);
> }
>
> -static void amd_iommu_apply_dm_region(struct device *dev,
> +static void amd_iommu_apply_resv_region(struct device *dev,
> struct iommu_domain *domain,
> - struct iommu_dm_region *region)
> + struct iommu_resv_region *region)
> {
> struct dma_ops_domain *dma_dom = to_dma_ops_domain(to_pdomain(domain));
> unsigned long start, end;
> @@ -3230,9 +3230,9 @@ static void amd_iommu_apply_dm_region(struct device *dev,
> .add_device = amd_iommu_add_device,
> .remove_device = amd_iommu_remove_device,
> .device_group = amd_iommu_device_group,
> - .get_dm_regions = amd_iommu_get_dm_regions,
> - .put_dm_regions = amd_iommu_put_dm_regions,
> - .apply_dm_region = amd_iommu_apply_dm_region,
> + .get_resv_regions = amd_iommu_get_resv_regions,
> + .put_resv_regions = amd_iommu_put_resv_regions,
> + .apply_resv_region = amd_iommu_apply_resv_region,
> .pgsize_bitmap = AMD_IOMMU_PGSIZES,
> };
>
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index dbe7f65..1cee5c3 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -318,7 +318,7 @@ static int iommu_group_create_direct_mappings(struct iommu_group *group,
> struct device *dev)
> {
> struct iommu_domain *domain = group->default_domain;
> - struct iommu_dm_region *entry;
> + struct iommu_resv_region *entry;
> struct list_head mappings;
> unsigned long pg_size;
> int ret = 0;
> @@ -331,14 +331,14 @@ static int iommu_group_create_direct_mappings(struct iommu_group *group,
> pg_size = 1UL << __ffs(domain->pgsize_bitmap);
> INIT_LIST_HEAD(&mappings);
>
> - iommu_get_dm_regions(dev, &mappings);
> + iommu_get_resv_regions(dev, &mappings);
>
> /* We need to consider overlapping regions for different devices */
> list_for_each_entry(entry, &mappings, list) {
> dma_addr_t start, end, addr;
>
> - if (domain->ops->apply_dm_region)
> - domain->ops->apply_dm_region(dev, domain, entry);
> + if (domain->ops->apply_resv_region)
> + domain->ops->apply_resv_region(dev, domain, entry);
>
> start = ALIGN(entry->start, pg_size);
> end = ALIGN(entry->start + entry->length, pg_size);
> @@ -358,7 +358,7 @@ static int iommu_group_create_direct_mappings(struct iommu_group *group,
> }
>
> out:
> - iommu_put_dm_regions(dev, &mappings);
> + iommu_put_resv_regions(dev, &mappings);
>
> return ret;
> }
> @@ -1559,20 +1559,20 @@ int iommu_domain_set_attr(struct iommu_domain *domain,
> }
> EXPORT_SYMBOL_GPL(iommu_domain_set_attr);
>
> -void iommu_get_dm_regions(struct device *dev, struct list_head *list)
> +void iommu_get_resv_regions(struct device *dev, struct list_head *list)
> {
> const struct iommu_ops *ops = dev->bus->iommu_ops;
>
> - if (ops && ops->get_dm_regions)
> - ops->get_dm_regions(dev, list);
> + if (ops && ops->get_resv_regions)
> + ops->get_resv_regions(dev, list);
> }
>
> -void iommu_put_dm_regions(struct device *dev, struct list_head *list)
> +void iommu_put_resv_regions(struct device *dev, struct list_head *list)
> {
> const struct iommu_ops *ops = dev->bus->iommu_ops;
>
> - if (ops && ops->put_dm_regions)
> - ops->put_dm_regions(dev, list);
> + if (ops && ops->put_resv_regions)
> + ops->put_resv_regions(dev, list);
> }
>
> /* Request that a device is direct mapped by the IOMMU */
> diff --git a/include/linux/iommu.h b/include/linux/iommu.h
> index 0ff5111..bfecb8b 100644
> --- a/include/linux/iommu.h
> +++ b/include/linux/iommu.h
> @@ -118,13 +118,13 @@ enum iommu_attr {
> };
>
> /**
> - * struct iommu_dm_region - descriptor for a direct mapped memory region
> + * struct iommu_resv_region - descriptor for a reserved memory region
> * @list: Linked list pointers
> * @start: System physical start address of the region
> * @length: Length of the region in bytes
> * @prot: IOMMU Protection flags (READ/WRITE/...)
> */
> -struct iommu_dm_region {
> +struct iommu_resv_region {
> struct list_head list;
> phys_addr_t start;
> size_t length;
> @@ -150,9 +150,9 @@ struct iommu_dm_region {
> * @device_group: find iommu group for a particular device
> * @domain_get_attr: Query domain attributes
> * @domain_set_attr: Change domain attributes
> - * @get_dm_regions: Request list of direct mapping requirements for a device
> - * @put_dm_regions: Free list of direct mapping requirements for a device
> - * @apply_dm_region: Temporary helper call-back for iova reserved ranges
> + * @get_resv_regions: Request list of reserved regions for a device
> + * @put_resv_regions: Free list of reserved regions for a device
> + * @apply_resv_region: Temporary helper call-back for iova reserved ranges
> * @domain_window_enable: Configure and enable a particular window for a domain
> * @domain_window_disable: Disable a particular window for a domain
> * @domain_set_windows: Set the number of windows for a domain
> @@ -184,11 +184,12 @@ struct iommu_ops {
> int (*domain_set_attr)(struct iommu_domain *domain,
> enum iommu_attr attr, void *data);
>
> - /* Request/Free a list of direct mapping requirements for a device */
> - void (*get_dm_regions)(struct device *dev, struct list_head *list);
> - void (*put_dm_regions)(struct device *dev, struct list_head *list);
> - void (*apply_dm_region)(struct device *dev, struct iommu_domain *domain,
> - struct iommu_dm_region *region);
> + /* Request/Free a list of reserved regions for a device */
> + void (*get_resv_regions)(struct device *dev, struct list_head *list);
> + void (*put_resv_regions)(struct device *dev, struct list_head *list);
> + void (*apply_resv_region)(struct device *dev,
> + struct iommu_domain *domain,
> + struct iommu_resv_region *region);
>
> /* Window handling functions */
> int (*domain_window_enable)(struct iommu_domain *domain, u32 wnd_nr,
> @@ -233,8 +234,8 @@ extern size_t default_iommu_map_sg(struct iommu_domain *domain, unsigned long io
> extern void iommu_set_fault_handler(struct iommu_domain *domain,
> iommu_fault_handler_t handler, void *token);
>
> -extern void iommu_get_dm_regions(struct device *dev, struct list_head *list);
> -extern void iommu_put_dm_regions(struct device *dev, struct list_head *list);
> +extern void iommu_get_resv_regions(struct device *dev, struct list_head *list);
> +extern void iommu_put_resv_regions(struct device *dev, struct list_head *list);
> extern int iommu_request_dm_for_dev(struct device *dev);
>
> extern int iommu_attach_group(struct iommu_domain *domain,
> @@ -443,12 +444,12 @@ static inline void iommu_set_fault_handler(struct iommu_domain *domain,
> {
> }
>
> -static inline void iommu_get_dm_regions(struct device *dev,
> +static inline void iommu_get_resv_regions(struct device *dev,
> struct list_head *list)
> {
> }
>
> -static inline void iommu_put_dm_regions(struct device *dev,
> +static inline void iommu_put_resv_regions(struct device *dev,
> struct list_head *list)
> {
> }
>
^ permalink raw reply
* [PATCH] clk: meson-gxbb: Export HDMI clocks
From: Neil Armstrong @ 2017-01-17 12:08 UTC (permalink / raw)
To: linux-arm-kernel
Export HDMI clock from internal to dt-bindings.
Signed-off-by: Neil Armstrong <narmstrong@baylibre.com>
---
drivers/clk/meson/gxbb.h | 4 ++--
include/dt-bindings/clock/gxbb-clkc.h | 2 ++
2 files changed, 4 insertions(+), 2 deletions(-)
diff --git a/drivers/clk/meson/gxbb.h b/drivers/clk/meson/gxbb.h
index 0252939..2139e97 100644
--- a/drivers/clk/meson/gxbb.h
+++ b/drivers/clk/meson/gxbb.h
@@ -231,7 +231,7 @@
#define CLKID_AHB_DATA_BUS 60
#define CLKID_AHB_CTRL_BUS 61
#define CLKID_HDMI_INTR_SYNC 62
-#define CLKID_HDMI_PCLK 63
+/* CLKID_HDMI_PCLK */
/* CLKID_USB1_DDR_BRIDGE */
/* CLKID_USB0_DDR_BRIDGE */
#define CLKID_MMC_PCLK 66
@@ -245,7 +245,7 @@
#define CLKID_VCLK2_VENCI1 74
#define CLKID_VCLK2_VENCP0 75
#define CLKID_VCLK2_VENCP1 76
-#define CLKID_GCLK_VENCI_INT0 77
+/* CLKID_GCLK_VENCI_INT0 */
#define CLKID_GCLK_VENCI_INT 78
#define CLKID_DAC_CLK 79
#define CLKID_AOCLK_GATE 80
diff --git a/include/dt-bindings/clock/gxbb-clkc.h b/include/dt-bindings/clock/gxbb-clkc.h
index baade6f..da1d473 100644
--- a/include/dt-bindings/clock/gxbb-clkc.h
+++ b/include/dt-bindings/clock/gxbb-clkc.h
@@ -18,8 +18,10 @@
#define CLKID_USB0 50
#define CLKID_USB1 51
#define CLKID_USB 55
+#define CLKID_HDMI_PCLK 63
#define CLKID_USB1_DDR_BRIDGE 64
#define CLKID_USB0_DDR_BRIDGE 65
+#define CLKID_GCLK_VENCI_INT0 77
#define CLKID_AO_I2C 93
#define CLKID_SD_EMMC_A 94
#define CLKID_SD_EMMC_B 95
--
1.9.1
^ permalink raw reply related
* [PATCH v8 04/18] iommu: iommu_alloc_resv_region
From: Tomasz Nowicki @ 2017-01-17 12:12 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484127714-3263-5-git-send-email-eric.auger@redhat.com>
On 11.01.2017 10:41, Eric Auger wrote:
> Introduce a new helper serving the purpose to allocate a reserved
> region. This will be used in iommu driver implementing reserved
> region callbacks.
>
> Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Tomasz Nowicki <tomasz.nowicki@caviumnetworks.com>
Thanks,
Tomasz
>
> ---
>
> v3 -> v4:
> - add INIT_LIST_HEAD(®ion->list)
> - use int for prot param and add int type param
> - remove implementation outside of CONFIG_IOMMU_API
> ---
> drivers/iommu/iommu.c | 18 ++++++++++++++++++
> include/linux/iommu.h | 2 ++
> 2 files changed, 20 insertions(+)
>
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index 1cee5c3..927878d 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -1575,6 +1575,24 @@ void iommu_put_resv_regions(struct device *dev, struct list_head *list)
> ops->put_resv_regions(dev, list);
> }
>
> +struct iommu_resv_region *iommu_alloc_resv_region(phys_addr_t start,
> + size_t length,
> + int prot, int type)
> +{
> + struct iommu_resv_region *region;
> +
> + region = kzalloc(sizeof(*region), GFP_KERNEL);
> + if (!region)
> + return NULL;
> +
> + INIT_LIST_HEAD(®ion->list);
> + region->start = start;
> + region->length = length;
> + region->prot = prot;
> + region->type = type;
> + return region;
> +}
> +
> /* Request that a device is direct mapped by the IOMMU */
> int iommu_request_dm_for_dev(struct device *dev)
> {
> diff --git a/include/linux/iommu.h b/include/linux/iommu.h
> index 233a6bf..f6bb55d3 100644
> --- a/include/linux/iommu.h
> +++ b/include/linux/iommu.h
> @@ -244,6 +244,8 @@ extern void iommu_set_fault_handler(struct iommu_domain *domain,
> extern void iommu_get_resv_regions(struct device *dev, struct list_head *list);
> extern void iommu_put_resv_regions(struct device *dev, struct list_head *list);
> extern int iommu_request_dm_for_dev(struct device *dev);
> +extern struct iommu_resv_region *
> +iommu_alloc_resv_region(phys_addr_t start, size_t length, int prot, int type);
>
> extern int iommu_attach_group(struct iommu_domain *domain,
> struct iommu_group *group);
>
^ permalink raw reply
* [PATCH v8 05/18] iommu: Only map direct mapped regions
From: Tomasz Nowicki @ 2017-01-17 12:13 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484127714-3263-6-git-send-email-eric.auger@redhat.com>
On 11.01.2017 10:41, Eric Auger wrote:
> As we introduced new reserved region types which do not require
> mapping, let's make sure we only map direct mapped regions.
>
> Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Tomasz Nowicki <tomasz.nowicki@caviumnetworks.com>
Thanks,
Tomasz
>
> ---
>
> v3 -> v4:
> - use region's type and reword commit message and title
> ---
> drivers/iommu/iommu.c | 3 +++
> 1 file changed, 3 insertions(+)
>
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index 927878d..41c1906 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -343,6 +343,9 @@ static int iommu_group_create_direct_mappings(struct iommu_group *group,
> start = ALIGN(entry->start, pg_size);
> end = ALIGN(entry->start + entry->length, pg_size);
>
> + if (entry->type != IOMMU_RESV_DIRECT)
> + continue;
> +
> for (addr = start; addr < end; addr += pg_size) {
> phys_addr_t phys_addr;
>
>
^ permalink raw reply
* [PATCH v8 06/18] iommu: iommu_get_group_resv_regions
From: Tomasz Nowicki @ 2017-01-17 12:14 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484127714-3263-7-git-send-email-eric.auger@redhat.com>
On 11.01.2017 10:41, Eric Auger wrote:
> Introduce iommu_get_group_resv_regions whose role consists in
> enumerating all devices from the group and collecting their
> reserved regions. The list is sorted and overlaps between
> regions of the same type are handled by merging the regions.
>
> Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Tomasz Nowicki <tomasz.nowicki@caviumnetworks.com>
Thanks,
Tomasz
>
> ---
> v6 -> v7:
> - avoid merge of regions of different type
>
> v3 -> v4:
> - take the iommu_group lock in iommu_get_group_resv_regions
> - the list now is sorted and overlaps are checked
>
> NOTE:
> - we do not move list elements from device to group list since
> the iommu_put_resv_regions() could not be called.
> - at the moment I did not introduce any iommu_put_group_resv_regions
> since it simply consists in voiding/freeing the list
> ---
> drivers/iommu/iommu.c | 98 +++++++++++++++++++++++++++++++++++++++++++++++++++
> include/linux/iommu.h | 8 +++++
> 2 files changed, 106 insertions(+)
>
> diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
> index 41c1906..640056b 100644
> --- a/drivers/iommu/iommu.c
> +++ b/drivers/iommu/iommu.c
> @@ -133,6 +133,104 @@ static ssize_t iommu_group_show_name(struct iommu_group *group, char *buf)
> return sprintf(buf, "%s\n", group->name);
> }
>
> +/**
> + * iommu_insert_resv_region - Insert a new region in the
> + * list of reserved regions.
> + * @new: new region to insert
> + * @regions: list of regions
> + *
> + * The new element is sorted by address with respect to the other
> + * regions of the same type. In case it overlaps with another
> + * region of the same type, regions are merged. In case it
> + * overlaps with another region of different type, regions are
> + * not merged.
> + */
> +static int iommu_insert_resv_region(struct iommu_resv_region *new,
> + struct list_head *regions)
> +{
> + struct iommu_resv_region *region;
> + phys_addr_t start = new->start;
> + phys_addr_t end = new->start + new->length - 1;
> + struct list_head *pos = regions->next;
> +
> + while (pos != regions) {
> + struct iommu_resv_region *entry =
> + list_entry(pos, struct iommu_resv_region, list);
> + phys_addr_t a = entry->start;
> + phys_addr_t b = entry->start + entry->length - 1;
> + int type = entry->type;
> +
> + if (end < a) {
> + goto insert;
> + } else if (start > b) {
> + pos = pos->next;
> + } else if ((start >= a) && (end <= b)) {
> + if (new->type == type)
> + goto done;
> + else
> + pos = pos->next;
> + } else {
> + if (new->type == type) {
> + phys_addr_t new_start = min(a, start);
> + phys_addr_t new_end = max(b, end);
> +
> + list_del(&entry->list);
> + entry->start = new_start;
> + entry->length = new_end - new_start + 1;
> + iommu_insert_resv_region(entry, regions);
> + } else {
> + pos = pos->next;
> + }
> + }
> + }
> +insert:
> + region = iommu_alloc_resv_region(new->start, new->length,
> + new->prot, new->type);
> + if (!region)
> + return -ENOMEM;
> +
> + list_add_tail(®ion->list, pos);
> +done:
> + return 0;
> +}
> +
> +static int
> +iommu_insert_device_resv_regions(struct list_head *dev_resv_regions,
> + struct list_head *group_resv_regions)
> +{
> + struct iommu_resv_region *entry;
> + int ret;
> +
> + list_for_each_entry(entry, dev_resv_regions, list) {
> + ret = iommu_insert_resv_region(entry, group_resv_regions);
> + if (ret)
> + break;
> + }
> + return ret;
> +}
> +
> +int iommu_get_group_resv_regions(struct iommu_group *group,
> + struct list_head *head)
> +{
> + struct iommu_device *device;
> + int ret = 0;
> +
> + mutex_lock(&group->mutex);
> + list_for_each_entry(device, &group->devices, list) {
> + struct list_head dev_resv_regions;
> +
> + INIT_LIST_HEAD(&dev_resv_regions);
> + iommu_get_resv_regions(device->dev, &dev_resv_regions);
> + ret = iommu_insert_device_resv_regions(&dev_resv_regions, head);
> + iommu_put_resv_regions(device->dev, &dev_resv_regions);
> + if (ret)
> + break;
> + }
> + mutex_unlock(&group->mutex);
> + return ret;
> +}
> +EXPORT_SYMBOL_GPL(iommu_get_group_resv_regions);
> +
> static IOMMU_GROUP_ATTR(name, S_IRUGO, iommu_group_show_name, NULL);
>
> static void iommu_group_release(struct kobject *kobj)
> diff --git a/include/linux/iommu.h b/include/linux/iommu.h
> index f6bb55d3..bec3730 100644
> --- a/include/linux/iommu.h
> +++ b/include/linux/iommu.h
> @@ -246,6 +246,8 @@ extern void iommu_set_fault_handler(struct iommu_domain *domain,
> extern int iommu_request_dm_for_dev(struct device *dev);
> extern struct iommu_resv_region *
> iommu_alloc_resv_region(phys_addr_t start, size_t length, int prot, int type);
> +extern int iommu_get_group_resv_regions(struct iommu_group *group,
> + struct list_head *head);
>
> extern int iommu_attach_group(struct iommu_domain *domain,
> struct iommu_group *group);
> @@ -463,6 +465,12 @@ static inline void iommu_put_resv_regions(struct device *dev,
> {
> }
>
> +static inline int iommu_get_group_resv_regions(struct iommu_group *group,
> + struct list_head *head)
> +{
> + return -ENODEV;
> +}
> +
> static inline int iommu_request_dm_for_dev(struct device *dev)
> {
> return -ENODEV;
>
^ permalink raw reply
* [PATCH] arm64: Fix swiotlb fallback allocation
From: Catalin Marinas @ 2017-01-17 12:14 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484567193-71258-1-git-send-email-agraf@suse.de>
On Mon, Jan 16, 2017 at 12:46:33PM +0100, Alexander Graf wrote:
> Commit b67a8b29df introduced logic to skip swiotlb allocation when all memory
> is DMA accessible anyway.
>
> While this is a great idea, __dma_alloc still calls swiotlb code unconditionally
> to allocate memory when there is no CMA memory available. The swiotlb code is
> called to ensure that we at least try get_free_pages().
>
> Without initialization, swiotlb allocation code tries to access io_tlb_list
> which is NULL. That results in a stack trace like this:
>
> Unable to handle kernel NULL pointer dereference at virtual address 00000000
> [...]
> [<ffff00000845b908>] swiotlb_tbl_map_single+0xd0/0x2b0
> [<ffff00000845be94>] swiotlb_alloc_coherent+0x10c/0x198
> [<ffff000008099dc0>] __dma_alloc+0x68/0x1a8
> [<ffff000000a1b410>] drm_gem_cma_create+0x98/0x108 [drm]
> [<ffff000000abcaac>] drm_fbdev_cma_create_with_funcs+0xbc/0x368 [drm_kms_helper]
> [<ffff000000abcd84>] drm_fbdev_cma_create+0x2c/0x40 [drm_kms_helper]
> [<ffff000000abc040>] drm_fb_helper_initial_config+0x238/0x410 [drm_kms_helper]
> [<ffff000000abce88>] drm_fbdev_cma_init_with_funcs+0x98/0x160 [drm_kms_helper]
> [<ffff000000abcf90>] drm_fbdev_cma_init+0x40/0x58 [drm_kms_helper]
> [<ffff000000b47980>] vc4_kms_load+0x90/0xf0 [vc4]
> [<ffff000000b46a94>] vc4_drm_bind+0xec/0x168 [vc4]
> [...]
>
> Thankfully swiotlb code just learned how to not do allocations with the FORCE_NO
> option. This patch configures the swiotlb code to use that if we decide not to
> initialize the swiotlb framework.
>
> Fixes: b67a8b29df ("arm64: mm: only initialize swiotlb when necessary")
> Signed-off-by: Alexander Graf <agraf@suse.de>
> CC: Catalin Marinas <catalin.marinas@arm.com>
> CC: Jisheng Zhang <jszhang@marvell.com>
> CC: Geert Uytterhoeven <geert+renesas@glider.be>
> CC: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Thanks for the fix.
BTW, I wonder whether we also need to improve the original commit
slightly, in case we get a device mask smaller than what max_pfn covers:
diff --git a/arch/arm64/mm/dma-mapping.c b/arch/arm64/mm/dma-mapping.c
index e04082700bb1..23090db2f5ba 100644
--- a/arch/arm64/mm/dma-mapping.c
+++ b/arch/arm64/mm/dma-mapping.c
@@ -349,7 +349,7 @@ static int __swiotlb_dma_supported(struct device *hwdev, u64 mask)
{
if (swiotlb)
return swiotlb_dma_supported(hwdev, mask);
- return 1;
+ return phys_to_dma(hwdev, PFN_PHYS(max_pfn) - 1) <= mask;
}
static struct dma_map_ops swiotlb_dma_ops = {
--
Catalin
^ permalink raw reply related
* [PATCH v4 0/4] arm64: dts: juno: CoreSight support updates
From: Sudeep Holla @ 2017-01-17 12:15 UTC (permalink / raw)
To: linux-arm-kernel
Juno r1/r2 boards have different CoreSight infrastructure outside the
CPU clusters. This patchset adds the additional coreSight components to
separate .dtsi files to support these differences.
v1->v2:
- moved the addition of the STM component into a separate patch
v2->v3:
- moved the back the common coreSight components back into
juno-base.dtsi
v3->v4:
- removed dtsi nesting in the existing Juno dts file to avoid
further addition of such nesting
- renamed some of the funnel and etf node names(which were
previously named confusing them to the labels
Mike Leach (2):
arm64: dts: juno: add CoreSight support for Juno r1/r2 variants
arm64: dts: juno: add missing CoreSight STM component
Sudeep Holla (2):
arm64: dts: juno: remove dtsi nesting inside tree structure
arm64: dts: juno: refactor CoreSight support on Juno r0
arch/arm64/boot/dts/arm/juno-base.dtsi | 41 ++++++++----
arch/arm64/boot/dts/arm/juno-clocks.dtsi | 3 +-
arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi | 100 ++++++++++++++++++++++++++++++
arch/arm64/boot/dts/arm/juno-r1.dts | 16 ++++-
arch/arm64/boot/dts/arm/juno-r2.dts | 16 ++++-
arch/arm64/boot/dts/arm/juno.dts | 27 +++++++-
6 files changed, 184 insertions(+), 19 deletions(-)
create mode 100644 arch/arm64/boot/dts/arm/juno-cs-r1r2.dtsi
--
2.7.4
^ permalink raw reply
* [PATCH v4 1/4] arm64: dts: juno: remove dtsi nesting inside tree structure
From: Sudeep Holla @ 2017-01-17 12:15 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484655313-9025-1-git-send-email-sudeep.holla@arm.com>
Currently juno-clock.dtsi and juno-base.dtsi are nested badly inside
the device tree structure. It's generally good practice to ensure that
individual dtsi stand by themselves at the top of the file.
This patch removes the nesting of the above mentioned dtsi files and
makes them independent.
Signed-off-by: Sudeep Holla <sudeep.holla@arm.com>
---
arch/arm64/boot/dts/arm/juno-base.dtsi | 6 ++++--
arch/arm64/boot/dts/arm/juno-clocks.dtsi | 3 ++-
arch/arm64/boot/dts/arm/juno-r1.dts | 3 +--
arch/arm64/boot/dts/arm/juno-r2.dts | 3 +--
arch/arm64/boot/dts/arm/juno.dts | 3 +--
5 files changed, 9 insertions(+), 9 deletions(-)
diff --git a/arch/arm64/boot/dts/arm/juno-base.dtsi b/arch/arm64/boot/dts/arm/juno-base.dtsi
index 7d832247d0db..580afaee978f 100644
--- a/arch/arm64/boot/dts/arm/juno-base.dtsi
+++ b/arch/arm64/boot/dts/arm/juno-base.dtsi
@@ -1,3 +1,6 @@
+#include "juno-clocks.dtsi"
+
+/ {
/*
* Devices shared by all Juno boards
*/
@@ -507,8 +510,6 @@
};
};
- /include/ "juno-clocks.dtsi"
-
smmu_dma: iommu at 7fb00000 {
compatible = "arm,mmu-401", "arm,smmu-v1";
reg = <0x0 0x7fb00000 0x0 0x10000>;
@@ -719,3 +720,4 @@
interrupt-map-mask = <0 0>;
interrupt-map = <0 0 &gic 0 0 0 168 IRQ_TYPE_LEVEL_HIGH>;
};
+};
diff --git a/arch/arm64/boot/dts/arm/juno-clocks.dtsi b/arch/arm64/boot/dts/arm/juno-clocks.dtsi
index 25352ed943e6..e5e265dfa902 100644
--- a/arch/arm64/boot/dts/arm/juno-clocks.dtsi
+++ b/arch/arm64/boot/dts/arm/juno-clocks.dtsi
@@ -6,7 +6,7 @@
* This file is licensed under a dual GPLv2 or BSD license.
*
*/
-
+/ {
/* SoC fixed clocks */
soc_uartclk: refclk7273800hz {
compatible = "fixed-clock";
@@ -42,3 +42,4 @@
clock-frequency = <400000000>;
clock-output-names = "faxi_clk";
};
+};
diff --git a/arch/arm64/boot/dts/arm/juno-r1.dts b/arch/arm64/boot/dts/arm/juno-r1.dts
index eec37feee8fc..b883a8afb6f4 100644
--- a/arch/arm64/boot/dts/arm/juno-r1.dts
+++ b/arch/arm64/boot/dts/arm/juno-r1.dts
@@ -9,6 +9,7 @@
/dts-v1/;
#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "juno-base.dtsi"
/ {
model = "ARM Juno development board (r1)";
@@ -176,8 +177,6 @@
<&A53_2>,
<&A53_3>;
};
-
- #include "juno-base.dtsi"
};
&memtimer {
diff --git a/arch/arm64/boot/dts/arm/juno-r2.dts b/arch/arm64/boot/dts/arm/juno-r2.dts
index 28f40ec44090..cfd8150bf30a 100644
--- a/arch/arm64/boot/dts/arm/juno-r2.dts
+++ b/arch/arm64/boot/dts/arm/juno-r2.dts
@@ -9,6 +9,7 @@
/dts-v1/;
#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "juno-base.dtsi"
/ {
model = "ARM Juno development board (r2)";
@@ -176,8 +177,6 @@
<&A53_2>,
<&A53_3>;
};
-
- #include "juno-base.dtsi"
};
&memtimer {
diff --git a/arch/arm64/boot/dts/arm/juno.dts b/arch/arm64/boot/dts/arm/juno.dts
index ac5ceb73f45f..9967c808a92d 100644
--- a/arch/arm64/boot/dts/arm/juno.dts
+++ b/arch/arm64/boot/dts/arm/juno.dts
@@ -9,6 +9,7 @@
/dts-v1/;
#include <dt-bindings/interrupt-controller/arm-gic.h>
+#include "juno-base.dtsi"
/ {
model = "ARM Juno development board (r0)";
@@ -176,8 +177,6 @@
<&A53_2>,
<&A53_3>;
};
-
- #include "juno-base.dtsi"
};
&etm0 {
--
2.7.4
^ permalink raw reply related
* [PATCH v4 2/4] arm64: dts: juno: refactor CoreSight support on Juno r0
From: Sudeep Holla @ 2017-01-17 12:15 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1484655313-9025-1-git-send-email-sudeep.holla@arm.com>
Currently the Coresight components are supported only on Juno r0
variant. In preparation to add support to Juno r1/r2 variants, this
patch refactors the existing coresight device nodes so that r1/r2
support can be added easily.
It also cleans up some of the device node names which were previously
named so as they were confused as the labels rather than the node names.
Reviewed-and-Tested-by: Mathieu Poirier <mathieu.poirier@linaro.org>
Signed-off-by: Sudeep Holla <sudeep.holla@arm.com>
---
arch/arm64/boot/dts/arm/juno-base.dtsi | 20 ++++++++++----------
arch/arm64/boot/dts/arm/juno.dts | 8 ++++++++
2 files changed, 18 insertions(+), 10 deletions(-)
diff --git a/arch/arm64/boot/dts/arm/juno-base.dtsi b/arch/arm64/boot/dts/arm/juno-base.dtsi
index 580afaee978f..faedf357db3b 100644
--- a/arch/arm64/boot/dts/arm/juno-base.dtsi
+++ b/arch/arm64/boot/dts/arm/juno-base.dtsi
@@ -86,7 +86,7 @@
* The actual size is just 4K though 64K is reserved. Access to the
* unmapped reserved region results in a DECERR response.
*/
- etf at 20010000 {
+ etf at 20010000 { /* ETF 0 */
compatible = "arm,coresight-tmc", "arm,primecell";
reg = <0 0x20010000 0 0x1000>;
@@ -100,7 +100,7 @@
/* input port */
port at 0 {
reg = <0>;
- etf_in_port: endpoint {
+ etf0_in_port: endpoint {
slave-mode;
remote-endpoint = <&main_funnel_out_port>;
};
@@ -109,8 +109,7 @@
/* output port */
port at 1 {
reg = <0>;
- etf_out_port: endpoint {
- remote-endpoint = <&replicator_in_port0>;
+ etf0_out_port: endpoint {
};
};
};
@@ -131,7 +130,8 @@
};
};
- main-funnel at 20040000 {
+ /* main funnel on Juno r0, cssys0 funnel on Juno r1/r2 as per TRM*/
+ main_funnel: funnel at 20040000 {
compatible = "arm,coresight-funnel", "arm,primecell";
reg = <0 0x20040000 0 0x1000>;
@@ -142,13 +142,15 @@
#address-cells = <1>;
#size-cells = <0>;
+ /* output port */
port at 0 {
reg = <0>;
main_funnel_out_port: endpoint {
- remote-endpoint = <&etf_in_port>;
+ remote-endpoint = <&etf0_in_port>;
};
};
+ /* input ports */
port at 1 {
reg = <0>;
main_funnel_in_port0: endpoint {
@@ -164,7 +166,6 @@
remote-endpoint = <&cluster1_funnel_out_port>;
};
};
-
};
};
@@ -198,7 +199,7 @@
};
};
- cluster0-funnel at 220c0000 {
+ funnel at 220c0000 { /* cluster0 funnel */
compatible = "arm,coresight-funnel", "arm,primecell";
reg = <0 0x220c0000 0 0x1000>;
@@ -262,7 +263,7 @@
};
};
- cluster1-funnel at 230c0000 {
+ funnel at 230c0000 { /* cluster1 funnel */
compatible = "arm,coresight-funnel", "arm,primecell";
reg = <0 0x230c0000 0 0x1000>;
@@ -385,7 +386,6 @@
reg = <0>;
replicator_in_port0: endpoint {
slave-mode;
- remote-endpoint = <&etf_out_port>;
};
};
};
diff --git a/arch/arm64/boot/dts/arm/juno.dts b/arch/arm64/boot/dts/arm/juno.dts
index 9967c808a92d..66fa4388d181 100644
--- a/arch/arm64/boot/dts/arm/juno.dts
+++ b/arch/arm64/boot/dts/arm/juno.dts
@@ -202,3 +202,11 @@
&etm5 {
cpu = <&A53_3>;
};
+
+&etf0_out_port {
+ remote-endpoint = <&replicator_in_port0>;
+};
+
+&replicator_in_port0 {
+ remote-endpoint = <&etf0_out_port>;
+};
--
2.7.4
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox