From patchwork Sat Oct 17 04:39:05 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bjorn Andersson X-Patchwork-Id: 11842587 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 23C1D16BC for ; Sat, 17 Oct 2020 05:54:54 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 086F420760 for ; Sat, 17 Oct 2020 05:54:54 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=linaro.org header.i=@linaro.org header.b="rNHXsdBX" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S2436778AbgJQFyx (ORCPT ); Sat, 17 Oct 2020 01:54:53 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56206 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S2436490AbgJQFyn (ORCPT ); Sat, 17 Oct 2020 01:54:43 -0400 Received: from mail-ot1-x344.google.com (mail-ot1-x344.google.com [IPv6:2607:f8b0:4864:20::344]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 6CF0AC05BD25 for ; Fri, 16 Oct 2020 21:38:28 -0700 (PDT) Received: by mail-ot1-x344.google.com with SMTP id m22so4514924ots.4 for ; Fri, 16 Oct 2020 21:38:28 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=5h+bbZ9M5fVwhu8jO4jzrcPr8WfAxCzDHuzDwBdlOrk=; b=rNHXsdBXLEHyHI2RbtLF4V+RV3DtpvRb55vdaj+0vbcqNM3iyJrndgp4TiL+sSOfr3 e0AsYtelaC5wjEzt3FP+QWDpBfk/IvCsu1QMR0dv59joHCX27jyqDodIs2L+Ckt2iwQh qWLIpwZTrZLpYr1AHQ7yp3zDLplJzgbWJreLhb7rZoRCc1jCPqZj/5xnwNCKjSHIjrrV b4Ga8ECvvDh71PkhkS0unaGFnITr5MaQUms98vloSxXVwu85ZDSMFW3jB3gmdWR6W1q9 c7mCK5R8pvCK6yklNFi3KTy6sBzqws49gVUJ1bj6ZlYLJue4pB5ca9tewh9hEtYo+ikp yMoA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=5h+bbZ9M5fVwhu8jO4jzrcPr8WfAxCzDHuzDwBdlOrk=; b=AeNjaT7R33wLXZjB9KcQEdIZ8ouygJrDxpaX3EsXDDl+X8Wr9EnnaoH6ck5CyqkCVS qAeRVtI2WihaRoPa8hilJ06sO3t6yZY12nGPYNarEO5BT7sUJyk3ucxl92XDtH23hzWd QePPMhRNIeNJgbvd7XHfI1yIO0/05UgjNVvdC5sr6RZa2wgCMtNQZPSAHBHOJ4CeHHIk 07y3Cut6jC2somzzeG11iE7jDCy2UmUBBMq/zNpMCKc/10YHbIzpSYRG5E/DSTF0EGkM LLYz2zcEyJZ9DoWXyFsWPcF/cBLY0UUloeks9sEDkr76SeYCiqXoQuhLySv6KbI9hPwO D5Fg== X-Gm-Message-State: AOAM530kKLV7K789/S4efPhGTxDuxavUQa/imQh8lejiGS+G6QZfb2N0 gH+iI0DTiyDlaqZR/pQSJKmQtA== X-Google-Smtp-Source: ABdhPJwpoWNiZybfRwwfJoWBdmsgXLsv0purd3mFs/NFe58vM0/ReOn+i8TlD+wvf2c+ue4teZCHtQ== X-Received: by 2002:a9d:3ee5:: with SMTP id b92mr5112404otc.156.1602909507748; Fri, 16 Oct 2020 21:38:27 -0700 (PDT) Received: from localhost.localdomain (104-57-184-186.lightspeed.austtx.sbcglobal.net. [104.57.184.186]) by smtp.gmail.com with ESMTPSA id t65sm1640038oib.50.2020.10.16.21.38.26 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 16 Oct 2020 21:38:27 -0700 (PDT) From: Bjorn Andersson To: Will Deacon , Robin Murphy , Joerg Roedel , Sai Prakash Ranjan , Jordan Crouse , Thierry Reding , Rob Clark Cc: linux-arm-kernel@lists.infradead.org, iommu@lists.linux-foundation.org, linux-kernel@vger.kernel.org, linux-arm-msm@vger.kernel.org Subject: [PATCH v4 1/3] iommu/arm-smmu: Allow implementation specific write_s2cr Date: Fri, 16 Oct 2020 21:39:05 -0700 Message-Id: <20201017043907.2656013-2-bjorn.andersson@linaro.org> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201017043907.2656013-1-bjorn.andersson@linaro.org> References: <20201017043907.2656013-1-bjorn.andersson@linaro.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-arm-msm@vger.kernel.org The firmware found in some Qualcomm platforms intercepts writes to the S2CR register in order to replace the BYPASS type with FAULT. Further more it treats faults at this level as catastrophic and restarts the device. Add support for providing implementation specific versions of the S2CR write function, to allow the Qualcomm driver to work around this behavior. Signed-off-by: Bjorn Andersson Reviewed-by: Robin Murphy --- Changes since v3: - New patch drivers/iommu/arm/arm-smmu/arm-smmu.c | 22 ++++++++++++++-------- drivers/iommu/arm/arm-smmu/arm-smmu.h | 1 + 2 files changed, 15 insertions(+), 8 deletions(-) diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu.c b/drivers/iommu/arm/arm-smmu/arm-smmu.c index dad7fa86fbd4..ed3f0428c110 100644 --- a/drivers/iommu/arm/arm-smmu/arm-smmu.c +++ b/drivers/iommu/arm/arm-smmu/arm-smmu.c @@ -929,14 +929,20 @@ static void arm_smmu_write_smr(struct arm_smmu_device *smmu, int idx) static void arm_smmu_write_s2cr(struct arm_smmu_device *smmu, int idx) { struct arm_smmu_s2cr *s2cr = smmu->s2crs + idx; - u32 reg = FIELD_PREP(ARM_SMMU_S2CR_TYPE, s2cr->type) | - FIELD_PREP(ARM_SMMU_S2CR_CBNDX, s2cr->cbndx) | - FIELD_PREP(ARM_SMMU_S2CR_PRIVCFG, s2cr->privcfg); - - if (smmu->features & ARM_SMMU_FEAT_EXIDS && smmu->smrs && - smmu->smrs[idx].valid) - reg |= ARM_SMMU_S2CR_EXIDVALID; - arm_smmu_gr0_write(smmu, ARM_SMMU_GR0_S2CR(idx), reg); + u32 reg; + + if (smmu->impl && smmu->impl->write_s2cr) { + smmu->impl->write_s2cr(smmu, idx); + } else { + reg = FIELD_PREP(ARM_SMMU_S2CR_TYPE, s2cr->type) | + FIELD_PREP(ARM_SMMU_S2CR_CBNDX, s2cr->cbndx) | + FIELD_PREP(ARM_SMMU_S2CR_PRIVCFG, s2cr->privcfg); + + if (smmu->features & ARM_SMMU_FEAT_EXIDS && smmu->smrs && + smmu->smrs[idx].valid) + reg |= ARM_SMMU_S2CR_EXIDVALID; + arm_smmu_gr0_write(smmu, ARM_SMMU_GR0_S2CR(idx), reg); + } } static void arm_smmu_write_sme(struct arm_smmu_device *smmu, int idx) diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu.h b/drivers/iommu/arm/arm-smmu/arm-smmu.h index 1a746476927c..b71647eaa319 100644 --- a/drivers/iommu/arm/arm-smmu/arm-smmu.h +++ b/drivers/iommu/arm/arm-smmu/arm-smmu.h @@ -436,6 +436,7 @@ struct arm_smmu_impl { int (*alloc_context_bank)(struct arm_smmu_domain *smmu_domain, struct arm_smmu_device *smmu, struct device *dev, int start); + void (*write_s2cr)(struct arm_smmu_device *smmu, int idx); }; #define INVALID_SMENDX -1 From patchwork Sat Oct 17 04:39:06 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bjorn Andersson X-Patchwork-Id: 11842589 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 003C016BC for ; Sat, 17 Oct 2020 05:54:56 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id DAFB520760 for ; Sat, 17 Oct 2020 05:54:55 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=linaro.org header.i=@linaro.org header.b="d49Vti2o" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S2436583AbgJQFyn (ORCPT ); Sat, 17 Oct 2020 01:54:43 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56196 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S2411851AbgJQFym (ORCPT ); Sat, 17 Oct 2020 01:54:42 -0400 Received: from mail-ot1-x341.google.com (mail-ot1-x341.google.com [IPv6:2607:f8b0:4864:20::341]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 82EEBC05BD26 for ; Fri, 16 Oct 2020 21:38:29 -0700 (PDT) Received: by mail-ot1-x341.google.com with SMTP id k68so59190otk.10 for ; Fri, 16 Oct 2020 21:38:29 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=AOjoMftzfUgquuonXm8ecKALCf35LLgxoRywnILvYmM=; b=d49Vti2ocqeySl7P9/9hAzXFqHuY26zRhnG4D5kODBWt7wOSQnaVdBrmHcNsY8o4zC wribtUA0xR6AfDS7810YK0Ia/ckWr7kzwXIuvVSz3U3C7D8H1WmhIY/F/C07ki2GhpqA IIWSRC9r9uzgAnaIJbfT0BSyxSYjIfiT2F4VPqnFilmwMEAAqyf4BiJG4Bn4Gpsx+DXm NuQ89kFrTA3k9Mvxt0vPlefFqDjm8ex6yvLO5HCL3rCuvFQGX3yHTVEmbE/LHmCj7+0y ShtfrggLu5Rto8X6HJ2UEqXUBWE59sy/+Qp9uNdlaMgUNUUJlk4A6MwkDvX7QpN6/WYR hyYw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=AOjoMftzfUgquuonXm8ecKALCf35LLgxoRywnILvYmM=; b=WRK3p3orV3fXzVIrp+G8iUc0hT1Gx1Y9VJGk9UR/J0heP4iELXaa3bMVfam0obkoHO uY1H3HxXmvc2o8gkvBAbHglqC4jMFkYQUWhFIlmsw4KywsY5oE1yNkBKqcDVYdFhPySp 0oc7gWmZNOtiw24QhOl/gX56ytG1csfnk8TofVpGk86E7jQIrI6I9HtTXo23hqra/Qy8 H3tHYiZnuy1gZWNMoyAXf1gAQ7qd83MaAJRyRgyZbN2pjkVphzVvC/b6kozU8W+NRNyG rz9Q/mCSBbhyNAxJqF+uANVgHWUQKXYabQRo8XDV4E5Vo06nadvajcgvLUlmApFljfC+ 9EgQ== X-Gm-Message-State: AOAM5321X/3o5Az3v+2UmgEFY2dl9Nu5NlQPxBpMi9yCCs6xR20o9dLQ 3D0oZK1keWQOV9Ruga3gx6HMBQ== X-Google-Smtp-Source: ABdhPJz3lO0k/8MmBGaECH28vrQgBXaTzrSnujfffItvlwzznAn3LCUQ2mYeix59JGLH13hqdqBk7Q== X-Received: by 2002:a9d:7993:: with SMTP id h19mr5086092otm.129.1602909508902; Fri, 16 Oct 2020 21:38:28 -0700 (PDT) Received: from localhost.localdomain (104-57-184-186.lightspeed.austtx.sbcglobal.net. [104.57.184.186]) by smtp.gmail.com with ESMTPSA id t65sm1640038oib.50.2020.10.16.21.38.27 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 16 Oct 2020 21:38:28 -0700 (PDT) From: Bjorn Andersson To: Will Deacon , Robin Murphy , Joerg Roedel , Sai Prakash Ranjan , Jordan Crouse , Thierry Reding , Rob Clark Cc: linux-arm-kernel@lists.infradead.org, iommu@lists.linux-foundation.org, linux-kernel@vger.kernel.org, linux-arm-msm@vger.kernel.org Subject: [PATCH v4 2/3] iommu/arm-smmu-qcom: Read back stream mappings Date: Fri, 16 Oct 2020 21:39:06 -0700 Message-Id: <20201017043907.2656013-3-bjorn.andersson@linaro.org> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201017043907.2656013-1-bjorn.andersson@linaro.org> References: <20201017043907.2656013-1-bjorn.andersson@linaro.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-arm-msm@vger.kernel.org The Qualcomm boot loader configures stream mapping for the peripherals that it accesses and in particular it sets up the stream mapping for the display controller to be allowed to scan out a splash screen or EFI framebuffer. Read back the stream mappings during initialization and make the arm-smmu driver maintain the streams in bypass mode. Signed-off-by: Bjorn Andersson --- Changes since v3: - Extracted from different patch in v3. - Now configures the stream as BYPASS, rather than translate, which should work for platforms with working S2CR handling as well. drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c | 24 ++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c index be4318044f96..0089048342dd 100644 --- a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c +++ b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c @@ -23,6 +23,29 @@ static const struct of_device_id qcom_smmu_client_of_match[] __maybe_unused = { { } }; +static int qcom_smmu_cfg_probe(struct arm_smmu_device *smmu) +{ + u32 smr; + int i; + + for (i = 0; i < smmu->num_mapping_groups; i++) { + smr = arm_smmu_gr0_read(smmu, ARM_SMMU_GR0_SMR(i)); + + if (FIELD_GET(ARM_SMMU_SMR_VALID, smr)) { + smmu->smrs[i].id = FIELD_GET(ARM_SMMU_SMR_ID, smr); + smmu->smrs[i].mask = FIELD_GET(ARM_SMMU_SMR_MASK, smr); + smmu->smrs[i].valid = true; + + smmu->s2crs[i].type = S2CR_TYPE_BYPASS; + smmu->s2crs[i].privcfg = S2CR_PRIVCFG_DEFAULT; + smmu->s2crs[i].cbndx = 0xff; + smmu->s2crs[i].count++; + } + } + + return 0; +} + static int qcom_smmu_def_domain_type(struct device *dev) { const struct of_device_id *match = @@ -61,6 +84,7 @@ static int qcom_smmu500_reset(struct arm_smmu_device *smmu) } static const struct arm_smmu_impl qcom_smmu_impl = { + .cfg_probe = qcom_smmu_cfg_probe, .def_domain_type = qcom_smmu_def_domain_type, .reset = qcom_smmu500_reset, }; From patchwork Sat Oct 17 04:39:07 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bjorn Andersson X-Patchwork-Id: 11842585 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id D9F3716BC for ; Sat, 17 Oct 2020 05:54:52 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id BAB4B207BC for ; Sat, 17 Oct 2020 05:54:52 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=linaro.org header.i=@linaro.org header.b="Tk/YA6qo" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S2436768AbgJQFyn (ORCPT ); Sat, 17 Oct 2020 01:54:43 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56198 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S2411862AbgJQFym (ORCPT ); Sat, 17 Oct 2020 01:54:42 -0400 Received: from mail-ot1-x341.google.com (mail-ot1-x341.google.com [IPv6:2607:f8b0:4864:20::341]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 933C2C05BD28 for ; Fri, 16 Oct 2020 21:38:30 -0700 (PDT) Received: by mail-ot1-x341.google.com with SMTP id i12so4500539ota.5 for ; Fri, 16 Oct 2020 21:38:30 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=R/eL9BOLO7lfTYwfmIUA3Aou+j6yOxaxr5STlBPy4E8=; b=Tk/YA6qo/6rOkDz5xz5TMpyb/nimdkJlU2E/WNrecuaem8ut0FqfNLxQpze6aI/o81 U4mvWAxfiHjKzj4PppSiggeSvuFmijySekSmYFElvLaMVfQHjGuxy4wvRDr7G6kqQZG1 r6d9JpAOfpJJSbcjoj2nLJyCuxlpDa4oOLAWXjjVXmTy9ZP3TSdR3RfgFIAI3n+YDToD NVyno5FjnfuvMuyD7kiaTVriaksYl2c4mePBekhgwlPoHfNIo/PeDDoqIgoN70E6Acsd r7imQQ/QlbUNQaw8OBvCQ2JnZgI/W5vVdDOBWRWxUTe7HwcY+tzKupk0Gxo04G22vTJd Fd6w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=R/eL9BOLO7lfTYwfmIUA3Aou+j6yOxaxr5STlBPy4E8=; b=mxqSqV8ky2LBhQ5pq5tPemI1zwgfyCaFMGHREnp6y3b0ImUhaO4m2mlhhg6sl1+0+B cymt8hUuEV4e/Dz6S0esCjICF0X433gGbkE6Xz0bQd1TZquT9HWp14XauVlgcJS9UW79 Awo7tgyO1nNNmTzXsu60rVM2DodWQEkKzIEDiaxiMwkeCjHhws1M00oGySwZVM23TvGH AOt4uZrEwxFKvWbr/Acdh1YY3xnN4MgZGEfroBOlcTzUpUC8VsbC2Nlp2NVAcNmjrA0k FCr2enVSIaQa1MfHBKkhLNxG+pxIwKy6AGB38V6nHIiGVuvBzmL/CSCB5bbMbttAxduG PnDw== X-Gm-Message-State: AOAM531+fJuKXYg5djDGZZvkob7IoezmbOFo0dtkLGP1xYeMFd+D+1Q4 iA0F4nZBwfqrL/H1zWztGH8lUmALm3s6nA== X-Google-Smtp-Source: ABdhPJwYTHQyiuBoo03LmtYktPRELqpF0a1iE0YTfXNgfPbXq/MBB3sgEV7hoaQd0dVnrJaUTkda5Q== X-Received: by 2002:a9d:7c87:: with SMTP id q7mr4988506otn.140.1602909509962; Fri, 16 Oct 2020 21:38:29 -0700 (PDT) Received: from localhost.localdomain (104-57-184-186.lightspeed.austtx.sbcglobal.net. [104.57.184.186]) by smtp.gmail.com with ESMTPSA id t65sm1640038oib.50.2020.10.16.21.38.28 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 16 Oct 2020 21:38:29 -0700 (PDT) From: Bjorn Andersson To: Will Deacon , Robin Murphy , Joerg Roedel , Sai Prakash Ranjan , Jordan Crouse , Thierry Reding , Rob Clark Cc: linux-arm-kernel@lists.infradead.org, iommu@lists.linux-foundation.org, linux-kernel@vger.kernel.org, linux-arm-msm@vger.kernel.org Subject: [PATCH v4 3/3] iommu/arm-smmu-qcom: Implement S2CR quirk Date: Fri, 16 Oct 2020 21:39:07 -0700 Message-Id: <20201017043907.2656013-4-bjorn.andersson@linaro.org> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201017043907.2656013-1-bjorn.andersson@linaro.org> References: <20201017043907.2656013-1-bjorn.andersson@linaro.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-arm-msm@vger.kernel.org The firmware found in some Qualcomm platforms intercepts writes to S2CR in order to replace bypass type streams with fault; and ignore S2CR updates of type fault. Detect this behavior and implement a custom write_s2cr function in order to trick the firmware into supporting bypass streams by the means of configuring the stream for translation using a reserved and disabled context bank. Also circumvent the problem of configuring faulting streams by configuring the stream as bypass. Signed-off-by: Bjorn Andersson --- Changes since v3: - Move the reservation of the "identity context bank" to the Qualcomm specific implementation. - Implement the S2CR quirk with the newly introduced write_s2cr callback. drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c | 68 ++++++++++++++++++++++ 1 file changed, 68 insertions(+) diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c index 0089048342dd..c0f42d6a6e01 100644 --- a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c +++ b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c @@ -10,8 +10,14 @@ struct qcom_smmu { struct arm_smmu_device smmu; + bool bypass_cbndx; }; +static struct qcom_smmu *to_qcom_smmu(struct arm_smmu_device *smmu) +{ + return container_of(smmu, struct qcom_smmu, smmu); +} + static const struct of_device_id qcom_smmu_client_of_match[] __maybe_unused = { { .compatible = "qcom,adreno" }, { .compatible = "qcom,mdp4" }, @@ -25,9 +31,32 @@ static const struct of_device_id qcom_smmu_client_of_match[] __maybe_unused = { static int qcom_smmu_cfg_probe(struct arm_smmu_device *smmu) { + unsigned int last_s2cr = ARM_SMMU_GR0_S2CR(smmu->num_mapping_groups - 1); + struct qcom_smmu *qsmmu = to_qcom_smmu(smmu); + u32 reg; u32 smr; int i; + /* + * With some firmware versions writes to S2CR of type FAULT are + * ignored, and writing BYPASS will end up written as FAULT in the + * register. Perform a write to S2CR to detect if this is the case and + * if so reserve a context bank to emulate bypass streams. + */ + reg = FIELD_PREP(ARM_SMMU_S2CR_TYPE, S2CR_TYPE_BYPASS) | + FIELD_PREP(ARM_SMMU_S2CR_CBNDX, 0xff) | + FIELD_PREP(ARM_SMMU_S2CR_PRIVCFG, S2CR_PRIVCFG_DEFAULT); + arm_smmu_gr0_write(smmu, last_s2cr, reg); + reg = arm_smmu_gr0_read(smmu, last_s2cr); + if (FIELD_GET(ARM_SMMU_S2CR_TYPE, reg) != S2CR_TYPE_BYPASS) { + qsmmu->bypass_cbndx = smmu->num_context_banks - 1; + + set_bit(qsmmu->bypass_cbndx, smmu->context_map); + + reg = FIELD_PREP(ARM_SMMU_CBAR_TYPE, CBAR_TYPE_S1_TRANS_S2_BYPASS); + arm_smmu_gr1_write(smmu, ARM_SMMU_GR1_CBAR(qsmmu->bypass_cbndx), reg); + } + for (i = 0; i < smmu->num_mapping_groups; i++) { smr = arm_smmu_gr0_read(smmu, ARM_SMMU_GR0_SMR(i)); @@ -46,6 +75,44 @@ static int qcom_smmu_cfg_probe(struct arm_smmu_device *smmu) return 0; } +static void qcom_smmu_write_s2cr(struct arm_smmu_device *smmu, int idx) +{ + struct arm_smmu_s2cr *s2cr = smmu->s2crs + idx; + struct qcom_smmu *qsmmu = to_qcom_smmu(smmu); + u32 cbndx = s2cr->cbndx; + u32 type = s2cr->type; + u32 reg; + + if (qsmmu->bypass_cbndx) { + if (type == S2CR_TYPE_BYPASS) { + /* + * Firmware with quirky S2CR handling will substitute + * BYPASS writes with FAULT, so point the stream to the + * reserved context bank and ask for translation on the + * stream + */ + type = S2CR_TYPE_TRANS; + cbndx = qsmmu->bypass_cbndx; + } else if (type == S2CR_TYPE_FAULT) { + /* + * Firmware with quirky S2CR handling will ignore FAULT + * writes, so trick it to write FAULT by asking for a + * BYPASS. + */ + type = S2CR_TYPE_BYPASS; + cbndx = 0xff; + } + } + + reg = FIELD_PREP(ARM_SMMU_S2CR_TYPE, type) | + FIELD_PREP(ARM_SMMU_S2CR_CBNDX, cbndx) | + FIELD_PREP(ARM_SMMU_S2CR_PRIVCFG, s2cr->privcfg); + + if (smmu->features & ARM_SMMU_FEAT_EXIDS && smmu->smrs && smmu->smrs[idx].valid) + reg |= ARM_SMMU_S2CR_EXIDVALID; + arm_smmu_gr0_write(smmu, ARM_SMMU_GR0_S2CR(idx), reg); +} + static int qcom_smmu_def_domain_type(struct device *dev) { const struct of_device_id *match = @@ -87,6 +154,7 @@ static const struct arm_smmu_impl qcom_smmu_impl = { .cfg_probe = qcom_smmu_cfg_probe, .def_domain_type = qcom_smmu_def_domain_type, .reset = qcom_smmu500_reset, + .write_s2cr = qcom_smmu_write_s2cr, }; struct arm_smmu_device *qcom_smmu_impl_init(struct arm_smmu_device *smmu)