public inbox for linux-arm-kernel@lists.infradead.org
 help / color / mirror / Atom feed
From: robin.murphy@arm.com (Robin Murphy)
To: linux-arm-kernel@lists.infradead.org
Subject: REGRESSION: iommu fails to take address limit into account
Date: Fri, 25 May 2018 11:49:01 +0100	[thread overview]
Message-ID: <6d95cd70-70bd-9e63-c148-d535fbedb0d0@arm.com> (raw)
In-Reply-To: <CAKv+Gu_0ECwLhoA2ywp3nntFX=RxfpM+MWFwTain1WN1sMrW9g@mail.gmail.com>

On 25/05/18 11:35, Ard Biesheuvel wrote:
> On 25 May 2018 at 11:48, Ard Biesheuvel <ard.biesheuvel@linaro.org> wrote:
>> Hello all,
>>
>> I am looking into an issue where a platform device is wired to a
>> MMU-500, and for some reason (which is under investigation) the
>> platform device can not drive all address bits. I can work around this
>> by limiting the DMA mask to 40 bits in the driver. However, the IORT
>> table allows me to set the address limit as well, and so I was
>> expecting this to be taken into account by the SMMU driver.
>>
>> When the iort/iommu layer sets up the DMA operations,
>> iommu_dma_init_domain() is entered with the expected values:
>>
>> base == 0
>> size == 0x100_0000_0000
>>
>> However, the iommu layer ends up generating IOVA addresses that have
>> bits [47:40] set (which is what the MMU-500 supports). Looking closer,
>> this is not surprising, given that the end_pfn variable that is
>> calculated in iommu_dma_init_domain() is no longer used after Zhen's
>> patch aa3ac9469c185 ("iommu/iova: Make dma_32bit_pfn implicit") was
>> applied.
>>
>> So effectively, this is a regression, and I would like your help
>> figuring out how to go about fixing this.
>>
> 
> I have narrowed it down a bit further: even though the IOVA range
> ignores the IORT address limit, the device's DMA mask is set
> correctly. The only problem is that the driver (like all drivers
> afaict) does not take into account the fact that its DMA mask has
> already been set by the bus layer before its probe function is called.
> 
> I could add something like this
> 
> -       if (dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(64)))
> +       if (dma_get_mask(&pdev->dev) == DMA_BIT_MASK(32) &&
> +           dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(64)))
>                  dev_warn(&pdev->dev, "Failed to enable 64-bit DMA\n");
> 
> to only override the mask if it is not at its default value, but it
> feels like papering over the problem given that most drivers appear to
> ignore the preset mask as well.

Yup, that's the crux of it - if, say, the firmware describes an explicit 
restriction to 32 bits, then drivers have no way to tell the difference 
between that and the default mask initialised by the bus code (which 
they *should* be able to widen), and at the moment neither does arch 
code or anyone else (and the current interface between arch code and 
firmware code does not help matters).

Robin.

  reply	other threads:[~2018-05-25 10:49 UTC|newest]

Thread overview: 5+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-05-25  9:48 REGRESSION: iommu fails to take address limit into account Ard Biesheuvel
2018-05-25 10:34 ` Robin Murphy
2018-05-25 10:35 ` Ard Biesheuvel
2018-05-25 10:49   ` Robin Murphy [this message]
2018-05-25 10:52     ` Ard Biesheuvel

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=6d95cd70-70bd-9e63-c148-d535fbedb0d0@arm.com \
    --to=robin.murphy@arm.com \
    --cc=linux-arm-kernel@lists.infradead.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox