Re: [PATCH v1 1/2] arm64: dts: mt6779: Support devapc

2020-12-23 Thread Neal Liu
+add comments & reviewed-by Hanks

On Wed, 2020-12-23 at 16:44 +0800, Neal Liu wrote:

Support DEVAPC on MT6779 platforms by adding device node.

Reviewed-by: Hanks Chen 
> Signed-off-by: Neal Liu 
> ---
>  arch/arm64/boot/dts/mediatek/mt6779.dtsi |8 
>  1 file changed, 8 insertions(+)
> 
> diff --git a/arch/arm64/boot/dts/mediatek/mt6779.dtsi 
> b/arch/arm64/boot/dts/mediatek/mt6779.dtsi
> index 370f309..52ecfc7 100644
> --- a/arch/arm64/boot/dts/mediatek/mt6779.dtsi
> +++ b/arch/arm64/boot/dts/mediatek/mt6779.dtsi
> @@ -189,6 +189,14 @@
>   #clock-cells = <1>;
>   };
>  
> + devapc: devapc@10207000 {
> + compatible = "mediatek,mt6779-devapc";
> + reg = <0 0x10207000 0 0x1000>;
> + interrupts = ;
> + clocks = <_ao CLK_INFRA_DEVICE_APC>;
> + clock-names = "devapc-infra-clock";
> + };
> +
>   uart0: serial@11002000 {
>   compatible = "mediatek,mt6779-uart",
>"mediatek,mt6577-uart";



[PATCH v1 1/2] arm64: dts: mt6779: Support devapc

2020-12-23 Thread Neal Liu
Signed-off-by: Neal Liu 
---
 arch/arm64/boot/dts/mediatek/mt6779.dtsi |8 
 1 file changed, 8 insertions(+)

diff --git a/arch/arm64/boot/dts/mediatek/mt6779.dtsi 
b/arch/arm64/boot/dts/mediatek/mt6779.dtsi
index 370f309..52ecfc7 100644
--- a/arch/arm64/boot/dts/mediatek/mt6779.dtsi
+++ b/arch/arm64/boot/dts/mediatek/mt6779.dtsi
@@ -189,6 +189,14 @@
#clock-cells = <1>;
};
 
+   devapc: devapc@10207000 {
+   compatible = "mediatek,mt6779-devapc";
+   reg = <0 0x10207000 0 0x1000>;
+   interrupts = ;
+   clocks = <_ao CLK_INFRA_DEVICE_APC>;
+   clock-names = "devapc-infra-clock";
+   };
+
uart0: serial@11002000 {
compatible = "mediatek,mt6779-uart",
 "mediatek,mt6577-uart";
-- 
1.7.9.5



[PATCH v1 0/2] arm64: Support devapc on MediaTek MT6779 platform

2020-12-23 Thread Neal Liu
This series adds DEVAPC (Device Access Permission Control) support on MediaTek 
MT6779 SoC platform.

*** BLURB HERE ***

Neal Liu (2):
  arm64: dts: mt6779: Support devapc
  arm64: configs: Support DEVAPC on MediaTek platforms

 arch/arm64/boot/dts/mediatek/mt6779.dtsi | 8 
 arch/arm64/configs/defconfig | 1 +
 2 files changed, 9 insertions(+)

-- 
2.18.0



[PATCH v1 2/2] arm64: configs: Support DEVAPC on MediaTek platforms

2020-12-23 Thread Neal Liu
Support DEVAPC on MediaTek platforms by enabling CONFIG_MTK_DEVAPC.

Signed-off-by: Neal Liu 
---
 arch/arm64/configs/defconfig |1 +
 1 file changed, 1 insertion(+)

diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig
index 17a2df6..a373776 100644
--- a/arch/arm64/configs/defconfig
+++ b/arch/arm64/configs/defconfig
@@ -257,6 +257,7 @@ CONFIG_MTD_NAND_MARVELL=y
 CONFIG_MTD_NAND_FSL_IFC=y
 CONFIG_MTD_NAND_QCOM=y
 CONFIG_MTD_SPI_NOR=y
+CONFIG_MTK_DEVAPC=m
 CONFIG_SPI_CADENCE_QUADSPI=y
 CONFIG_BLK_DEV_LOOP=y
 CONFIG_BLK_DEV_NBD=m
-- 
1.7.9.5



Re: [PATCH v8] Add MediaTek MT6779 devapc driver

2020-11-01 Thread Neal Liu
Gentle ping for these patch series.
Thanks !

On Thu, 2020-10-15 at 11:24 +0800, Neal Liu wrote:
> add subject
> 
> On Thu, 2020-10-15 at 11:20 +0800, Neal Liu wrote:
> > These patch series introduce a MediaTek MT6779 devapc driver.
> > 
> > MediaTek bus fabric provides TrustZone security support and data protection 
> > to prevent slaves from being accessed by unexpected masters.
> > The security violation is logged and sent to the processor for further 
> > analysis or countermeasures.
> > 
> > Any occurrence of security violation would raise an interrupt, and it will 
> > be handled by mtk-devapc driver.
> > The violation information is printed in order to find the murderer.
> > 
> > changes since v7:
> > - fix VIO_MOD_TO_REG_IND calculation wrong problem.
> > - revise parameter type of ISR.
> > 
> > changes since v6:
> > - remove unnecessary mask/unmask module irq during ISR.
> > 
> > changes since v5:
> > - remove redundant write reg operation.
> > - use static variable of vio_dbgs instead.
> > - add stop_devapc() if driver is removed.
> > 
> > changes since v4:
> > - refactor data structure.
> > - merge two simple functions into one.
> > - refactor register setting to prevent too many function call overhead.
> > 
> > changes since v3:
> > - revise violation handling flow to make it more easily to understand
> >   hardware behavior.
> > - add more comments to understand how hardware works.
> > 
> > changes since v2:
> > - pass platform info through DT data.
> > - remove unnecessary function.
> > - remove slave_type because it always equals to 1 in current support SoC.
> > - use vio_idx_num instread of list all devices' index.
> > - add more comments to describe hardware behavior.
> > 
> > changes since v1:
> > - move SoC specific part to DT data.
> > - remove unnecessary boundary check.
> > - remove unnecessary data type declaration.
> > - use read_poll_timeout() instread of for loop polling.
> > - revise coding style elegantly.
> > 
> > 
> > *** BLURB HERE ***
> > 
> > Neal Liu (2):
> >   dt-bindings: devapc: add bindings for mtk-devapc
> >   soc: mediatek: add mt6779 devapc driver
> > 
> >  .../bindings/soc/mediatek/devapc.yaml |  58 
> >  drivers/soc/mediatek/Kconfig  |   9 +
> >  drivers/soc/mediatek/Makefile |   1 +
> >  drivers/soc/mediatek/mtk-devapc.c | 308 ++
> >  4 files changed, 376 insertions(+)
> >  create mode 100644 
> > Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> >  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> > 
> 
> 



[PATCH v8] Add MediaTek MT6779 devapc driver

2020-10-14 Thread Neal Liu
add subject

On Thu, 2020-10-15 at 11:20 +0800, Neal Liu wrote:
> These patch series introduce a MediaTek MT6779 devapc driver.
> 
> MediaTek bus fabric provides TrustZone security support and data protection 
> to prevent slaves from being accessed by unexpected masters.
> The security violation is logged and sent to the processor for further 
> analysis or countermeasures.
> 
> Any occurrence of security violation would raise an interrupt, and it will be 
> handled by mtk-devapc driver.
> The violation information is printed in order to find the murderer.
> 
> changes since v7:
> - fix VIO_MOD_TO_REG_IND calculation wrong problem.
> - revise parameter type of ISR.
> 
> changes since v6:
> - remove unnecessary mask/unmask module irq during ISR.
> 
> changes since v5:
> - remove redundant write reg operation.
> - use static variable of vio_dbgs instead.
> - add stop_devapc() if driver is removed.
> 
> changes since v4:
> - refactor data structure.
> - merge two simple functions into one.
> - refactor register setting to prevent too many function call overhead.
> 
> changes since v3:
> - revise violation handling flow to make it more easily to understand
>   hardware behavior.
> - add more comments to understand how hardware works.
> 
> changes since v2:
> - pass platform info through DT data.
> - remove unnecessary function.
> - remove slave_type because it always equals to 1 in current support SoC.
> - use vio_idx_num instread of list all devices' index.
> - add more comments to describe hardware behavior.
> 
> changes since v1:
> - move SoC specific part to DT data.
> - remove unnecessary boundary check.
> - remove unnecessary data type declaration.
> - use read_poll_timeout() instread of for loop polling.
> - revise coding style elegantly.
> 
> 
> *** BLURB HERE ***
> 
> Neal Liu (2):
>   dt-bindings: devapc: add bindings for mtk-devapc
>   soc: mediatek: add mt6779 devapc driver
> 
>  .../bindings/soc/mediatek/devapc.yaml |  58 
>  drivers/soc/mediatek/Kconfig  |   9 +
>  drivers/soc/mediatek/Makefile |   1 +
>  drivers/soc/mediatek/mtk-devapc.c | 308 ++
>  4 files changed, 376 insertions(+)
>  create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
>  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> 



[PATCH v8 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-10-14 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..6c763f8
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


[no subject]

2020-10-14 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further analysis 
or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v7:
- fix VIO_MOD_TO_REG_IND calculation wrong problem.
- revise parameter type of ISR.

changes since v6:
- remove unnecessary mask/unmask module irq during ISR.

changes since v5:
- remove redundant write reg operation.
- use static variable of vio_dbgs instead.
- add stop_devapc() if driver is removed.

changes since v4:
- refactor data structure.
- merge two simple functions into one.
- refactor register setting to prevent too many function call overhead.

changes since v3:
- revise violation handling flow to make it more easily to understand
  hardware behavior.
- add more comments to understand how hardware works.

changes since v2:
- pass platform info through DT data.
- remove unnecessary function.
- remove slave_type because it always equals to 1 in current support SoC.
- use vio_idx_num instread of list all devices' index.
- add more comments to describe hardware behavior.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mt6779 devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  58 
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 308 ++
 4 files changed, 376 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

-- 
2.18.0


[PATCH v8 2/2] soc: mediatek: add mt6779 devapc driver

2020-10-14 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 ++
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  308 +
 3 files changed, 318 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..f1cea04
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,308 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#define VIO_MOD_TO_REG_IND(m)  ((m) / 32)
+#define VIO_MOD_TO_REG_OFF(m)  ((m) % 32)
+
+struct mtk_devapc_vio_dbgs {
+   union {
+   u32 vio_dbg0;
+   struct {
+   u32 mstid:16;
+   u32 dmnid:6;
+   u32 vio_w:1;
+   u32 vio_r:1;
+   u32 addr_h:4;
+   u32 resv:4;
+   } dbg0_bits;
+   };
+
+   u32 vio_dbg1;
+};
+
+struct mtk_devapc_data {
+   /* numbers of violation index */
+   u32 vio_idx_num;
+
+   /* reg offset */
+   u32 vio_mask_offset;
+   u32 vio_sta_offset;
+   u32 vio_dbg0_offset;
+   u32 vio_dbg1_offset;
+   u32 apc_con_offset;
+   u32 vio_shift_sta_offset;
+   u32 vio_shift_sel_offset;
+   u32 vio_shift_con_offset;
+};
+
+struct mtk_devapc_context {
+   struct device *dev;
+   void __iomem *infra_base;
+   struct clk *infra_clk;
+   const struct mtk_devapc_data *data;
+};
+
+static void clear_vio_status(struct mtk_devapc_context *ctx)
+{
+   void __iomem *reg;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_sta_offset;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num) - 1; i++)
+   writel(GENMASK(31, 0), reg + 4 * i);
+
+   writel(GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num) - 1, 0),
+  reg + 4 * i);
+}
+
+static void mask_module_irq(struct mtk_devapc_context *ctx, bool mask)
+{
+   void __iomem *reg;
+   u32 val;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_mask_offset;
+
+   if (mask)
+   val = GENMASK(31, 0);
+   else
+   val = 0;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num) - 1; i++)
+   writel(val, reg + 4 * i);
+
+   val = readl(reg + 4 * i);
+   if (mask)
+   val |= GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num) - 1,
+  0);
+   else
+   val &= ~GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num) - 1,
+   0);
+
+   writel(val, reg + 4 * i);
+}
+
+#define PHY_DEVAPC_TIMEOUT 0x1
+
+/*
+ * devapc_sync_vio_dbg - do "shift" mechansim" to get full violation 
information.
+ *   shift mechanism is depends on devapc hardware design.
+ *   Mediatek devapc set multiple slaves as a group.
+ *   When violation is triggered, violation info is kept
+ *   inside devapc hardware.
+ * 

Re: [PATCH v7 2/2] soc: mediatek: add mt6779 devapc driver

2020-10-14 Thread Neal Liu
On Thu, 2020-10-08 at 10:35 +0800, Neal Liu wrote:
> On Wed, 2020-10-07 at 12:44 +0200, Matthias Brugger wrote:
> > 
> > On 27/08/2020 05:06, Neal Liu wrote:
[...]

> > > +static int devapc_sync_vio_dbg(struct mtk_devapc_context *ctx)
> > > +{
> > > + void __iomem *pd_vio_shift_sta_reg;
> > > + void __iomem *pd_vio_shift_sel_reg;
> > > + void __iomem *pd_vio_shift_con_reg;
> > > + int min_shift_group;
> > > + int ret;
> > > + u32 val;
> > > +
> > > + pd_vio_shift_sta_reg = ctx->infra_base +
> > > +ctx->data->vio_shift_sta_offset;
> > > + pd_vio_shift_sel_reg = ctx->infra_base +
> > > +ctx->data->vio_shift_sel_offset;
> > > + pd_vio_shift_con_reg = ctx->infra_base +
> > > +ctx->data->vio_shift_con_offset;
> > > +
> > > + /* Find the minimum shift group which has violation */
> > > + val = readl(pd_vio_shift_sta_reg);
> > > + if (!val)
> > > + return false;
> > 
> > So bit 0 of selection register (pd_vio_shift_sel_reg) does not represent a 
> > violation group?
> > I don't know how the HW works, but is seems odd to me. In case that's bit 0 
> > actually doesn't represent anything: how can an interrupt be triggered 
> > without 
> > any debug information present (means val == 0)?
> 
> This check implies HW status has something wrong. It cannot get any
> debug information for this case.
> It won't happen in normal scenario. Should we remove this check?
> 

Sorry, I missed the most common part. Is function is in the while loop:
while (devapc_sync_vio_dbg(ctx))
...

We keep find the minimum bit in pd_vio_shift_sta_reg to get the
violation information, (pd_vio_shift_sta_reg might raise multiple bits)
until all raised bit (shift group) has been handled.
So I don't think it's necessary to add WARN message in this case.
Thanks

> > 
> > > +
> > > + min_shift_group = __ffs(val);
> > > +
> > > + /* Assign the group to sync */
> > > + writel(0x1 << min_shift_group, pd_vio_shift_sel_reg);
> > > +
> > > + /* Start syncing */
> > > + writel(0x1, pd_vio_shift_con_reg);
> > > +
> > > + ret = readl_poll_timeout(pd_vio_shift_con_reg, val, val == 0x3, 0,
> > > +  PHY_DEVAPC_TIMEOUT);
> > > + if (ret) {
> > > + dev_err(ctx->dev, "%s: Shift violation info failed\n", 
> > > __func__);
> > 
> > In which case this can happen? I'm asking, because we are calling 
> > devapc_sync_vio_dbg() in a while loop that could make the kernel hang here.
> > 
> > Do I understand correctly, that we are using the while loop, because there 
> > can 
> > be more then one violation group which got triggered (read, more then one 
> > bit is 
> > set in pd_vio_shift_sta_reg)? Would it make more sense then to read the 
> > register 
> > once and do all the shift operation for all groups which bit set to 1 in 
> > the 
> > shift status register?
> 
> Yes, your understanding is correct.
> This check also implies HW status has something wrong. We return false
> to skip further violation info dump.
> How could this case make the kernel hang?
> 
> > 
> > > + return false;
> > > + }
> > > +
> > > + /* Stop syncing */
> > > + writel(0x0, pd_vio_shift_con_reg);
> > > +
> > > + /* Write clear */
> > > + writel(0x1 << min_shift_group, pd_vio_shift_sta_reg);
> > > +
> > > + return true;
> > > +}
> > > +
> > > +/*
> > > + * devapc_extract_vio_dbg - extract full violation information after 
> > > doing
> > > + *  shift mechanism.
> > > + */
> > > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > > +{
> > > + struct mtk_devapc_vio_dbgs vio_dbgs;
> > > + void __iomem *vio_dbg0_reg;
> > > + void __iomem *vio_dbg1_reg;
> > > +
> > > + vio_dbg0_reg = ctx->infra_base + ctx->data->vio_dbg0_offset;
> > > + vio_dbg1_reg = ctx->infra_base + ctx->data->vio_dbg1_offset;
> > > +
> > > + vio_dbgs.vio_dbg0 = readl(vio_dbg0_reg);
> > > + vio_dbgs.vio_dbg1 = readl(vio_dbg1_reg);
> > > +
> > > + /* Print violation information */
> > > + if (vio_dbgs.dbg0_bits.vio_w)
> > > + dev_info(ctx->dev, "Write Violation\n");
> > > + else if (vio_dbgs.dbg0_bi

Re: [PATCH v7 2/2] soc: mediatek: add mt6779 devapc driver

2020-10-11 Thread Neal Liu
On Fri, 2020-10-09 at 14:34 +0200, Matthias Brugger wrote:
> 
> On 08/10/2020 11:39, Neal Liu wrote:
> > On Thu, 2020-10-08 at 10:45 +0200, Matthias Brugger wrote:
> >>
> >> On 08/10/2020 04:35, Neal Liu wrote:
> >>> On Wed, 2020-10-07 at 12:44 +0200, Matthias Brugger wrote:
> >>>>
> >>>> On 27/08/2020 05:06, Neal Liu wrote:
> [...]
> 
> >>>>> +static int mtk_devapc_probe(struct platform_device *pdev)
> >>>>> +{
> >>>>> +   struct device_node *node = pdev->dev.of_node;
> >>>>> +   struct mtk_devapc_context *ctx;
> >>>>> +   u32 devapc_irq;
> >>>>> +   int ret;
> >>>>> +
> >>>>> +   if (IS_ERR(node))
> >>>>> +   return -ENODEV;
> >>>>> +
> >>>>> +   ctx = devm_kzalloc(>dev, sizeof(*ctx), GFP_KERNEL);
> >>>>> +   if (!ctx)
> >>>>> +   return -ENOMEM;
> >>>>> +
> >>>>> +   ctx->data = of_device_get_match_data(>dev);
> >>>>> +   ctx->dev = >dev;
> >>>>> +
> >>>>> +   ctx->infra_base = of_iomap(node, 0);
> >>>>
> >>>> Does this mean the device is part of the infracfg block?
> >>>> I wasn't able to find any information about it.
> >>>
> >>> I'm not sure why you would ask infracfg block. devapc is parts of our
> >>> SoC infra, it's different with infracfg.
> >>>
> >>
> >> I'm asking because I want to understand the HW better. I'm not able to 
> >> find any
> >> information in the datasheets. I want to avoid a situation as we had with 
> >> the
> >> MMSYS where a clock driver was submitted first and later on we realized 
> >> that
> >> MMSYS is much more then that and we had to work hard to get the driver 
> >> right.
> >>
> >> Now it's happening with SCPSYS, where a driver with the scpsys compatible 
> >> was
> >> send years ago. But SCPSYS is much more then the driver submitted. In this 
> >> case
> >> we opted to write a new driver, but moving from one driver to another one 
> >> is
> >> painfull and full of problems. For that I want to make sure we fully 
> >> understand
> >> Device APC (by the way, what does APC stands for?). Is it a totally 
> >> independent
> >> HW block or is it part of a subsystem, like for example SCP?
> >>
> >> Regards,
> >> Matthias
> > 
> > It's a totally independent HW block instead of a subsystem.
> > I think it's more simple than MMSYS or SCPSYS. But if you would like to
> > understand more about this HW, we could find another way/channel to
> > introduce it.
> > 
> 
> If it's a independent HW block, then we are good. No further information 
> needed 
> by me. I'd just advise to rename the infra_base to something like base, as it 
> made me confuse.
> 
> Thanks!
> Matthias

You can imagine that infra_base means infra devapc base address for
MT6779. In 5G platforms, MediaTek infrastructure would separate into
multiple parts, so does devapc HW. And devapc would be like:
infra_base, peri_base, peri2_base, ...

Thanks.



Re: [PATCH v7 2/2] soc: mediatek: add mt6779 devapc driver

2020-10-08 Thread Neal Liu
On Thu, 2020-10-08 at 10:45 +0200, Matthias Brugger wrote:
> 
> On 08/10/2020 04:35, Neal Liu wrote:
> > On Wed, 2020-10-07 at 12:44 +0200, Matthias Brugger wrote:
> >>
> >> On 27/08/2020 05:06, Neal Liu wrote:
> >>> MediaTek bus fabric provides TrustZone security support and data
> >>> protection to prevent slaves from being accessed by unexpected
> >>> masters.
> >>> The security violation is logged and sent to the processor for
> >>> further analysis or countermeasures.
> >>>
> >>> Any occurrence of security violation would raise an interrupt, and
> >>> it will be handled by mtk-devapc driver. The violation
> >>> information is printed in order to find the murderer.
> >>
> >> "The violation information is printed in order to find the responsible 
> >> component."
> >>
> >> Nobody got actually killed, right :)
> > 
> > Correct !
> >>
> >>>
> >>> Signed-off-by: Neal Liu 
> >>> ---
> >>>drivers/soc/mediatek/Kconfig  |9 ++
> >>>drivers/soc/mediatek/Makefile |1 +
> >>>drivers/soc/mediatek/mtk-devapc.c |  305 
> >>> +
> >>>3 files changed, 315 insertions(+)
> >>>create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> >>>
> >>> diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
> >>> index 59a56cd..1177c98 100644
> >>> --- a/drivers/soc/mediatek/Kconfig
> >>> +++ b/drivers/soc/mediatek/Kconfig
> >>> @@ -17,6 +17,15 @@ config MTK_CMDQ
> >>> time limitation, such as updating display configuration 
> >>> during the
> >>> vblank.
> >>>
> >>> +config MTK_DEVAPC
> >>> + tristate "Mediatek Device APC Support"
> >>> + help
> >>> +   Say yes here to enable support for Mediatek Device APC driver.
> >>> +   This driver is mainly used to handle the violation which catches
> >>> +   unexpected transaction.
> >>> +   The violation information is logged for further analysis or
> >>> +   countermeasures.
> >>> +
> >>>config MTK_INFRACFG
> >>>   bool "MediaTek INFRACFG Support"
> >>>   select REGMAP
> >>> diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
> >>> index 01f9f87..abfd4ba 100644
> >>> --- a/drivers/soc/mediatek/Makefile
> >>> +++ b/drivers/soc/mediatek/Makefile
> >>> @@ -1,5 +1,6 @@
> >>># SPDX-License-Identifier: GPL-2.0-only
> >>>obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
> >>> +obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
> >>>obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
> >>>obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
> >>>obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
> >>> diff --git a/drivers/soc/mediatek/mtk-devapc.c 
> >>> b/drivers/soc/mediatek/mtk-devapc.c
> >>> new file mode 100644
> >>> index 000..0ba61d7
> >>> --- /dev/null
> >>> +++ b/drivers/soc/mediatek/mtk-devapc.c
> >>> @@ -0,0 +1,305 @@
> >>> +// SPDX-License-Identifier: GPL-2.0
> >>> +/*
> >>> + * Copyright (C) 2020 MediaTek Inc.
> >>> + */
> >>> +
> >>> +#include 
> >>> +#include 
> >>> +#include 
> >>> +#include 
> >>> +#include 
> >>> +#include 
> >>> +#include 
> >>> +#include 
> >>> +
> >>> +#define VIO_MOD_TO_REG_IND(m)((m) / 32)
> >>> +#define VIO_MOD_TO_REG_OFF(m)((m) % 32)
> >>> +
> >>> +struct mtk_devapc_vio_dbgs {
> >>> + union {
> >>> + u32 vio_dbg0;
> >>> + struct {
> >>> + u32 mstid:16;
> >>> + u32 dmnid:6;
> >>> + u32 vio_w:1;
> >>> + u32 vio_r:1;
> >>> + u32 addr_h:4;
> >>> + u32 resv:4;
> >>> + } dbg0_bits;
> >>> + };
> >>> +
> >>> + u32 vio_dbg1;
> >>> +};
> >>> +
> >>> +struct mtk_devapc_data {
> >>> + u32 vio_idx_num;
> >>> + u32 vio_mask_offset;
> >>> + u32

Re: [PATCH v7 2/2] soc: mediatek: add mt6779 devapc driver

2020-10-07 Thread Neal Liu
On Wed, 2020-10-07 at 12:44 +0200, Matthias Brugger wrote:
> 
> On 27/08/2020 05:06, Neal Liu wrote:
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> > 
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> 
> "The violation information is printed in order to find the responsible 
> component."
> 
> Nobody got actually killed, right :)

Correct !
> 
> > 
> > Signed-off-by: Neal Liu 
> > ---
> >   drivers/soc/mediatek/Kconfig  |9 ++
> >   drivers/soc/mediatek/Makefile |1 +
> >   drivers/soc/mediatek/mtk-devapc.c |  305 
> > +
> >   3 files changed, 315 insertions(+)
> >   create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> > 
> > diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
> > index 59a56cd..1177c98 100644
> > --- a/drivers/soc/mediatek/Kconfig
> > +++ b/drivers/soc/mediatek/Kconfig
> > @@ -17,6 +17,15 @@ config MTK_CMDQ
> >   time limitation, such as updating display configuration during the
> >   vblank.
> >   
> > +config MTK_DEVAPC
> > +   tristate "Mediatek Device APC Support"
> > +   help
> > + Say yes here to enable support for Mediatek Device APC driver.
> > + This driver is mainly used to handle the violation which catches
> > + unexpected transaction.
> > + The violation information is logged for further analysis or
> > + countermeasures.
> > +
> >   config MTK_INFRACFG
> > bool "MediaTek INFRACFG Support"
> > select REGMAP
> > diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
> > index 01f9f87..abfd4ba 100644
> > --- a/drivers/soc/mediatek/Makefile
> > +++ b/drivers/soc/mediatek/Makefile
> > @@ -1,5 +1,6 @@
> >   # SPDX-License-Identifier: GPL-2.0-only
> >   obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
> > +obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
> >   obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
> >   obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
> >   obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
> > diff --git a/drivers/soc/mediatek/mtk-devapc.c 
> > b/drivers/soc/mediatek/mtk-devapc.c
> > new file mode 100644
> > index 000..0ba61d7
> > --- /dev/null
> > +++ b/drivers/soc/mediatek/mtk-devapc.c
> > @@ -0,0 +1,305 @@
> > +// SPDX-License-Identifier: GPL-2.0
> > +/*
> > + * Copyright (C) 2020 MediaTek Inc.
> > + */
> > +
> > +#include 
> > +#include 
> > +#include 
> > +#include 
> > +#include 
> > +#include 
> > +#include 
> > +#include 
> > +
> > +#define VIO_MOD_TO_REG_IND(m)  ((m) / 32)
> > +#define VIO_MOD_TO_REG_OFF(m)  ((m) % 32)
> > +
> > +struct mtk_devapc_vio_dbgs {
> > +   union {
> > +   u32 vio_dbg0;
> > +   struct {
> > +   u32 mstid:16;
> > +   u32 dmnid:6;
> > +   u32 vio_w:1;
> > +   u32 vio_r:1;
> > +   u32 addr_h:4;
> > +   u32 resv:4;
> > +   } dbg0_bits;
> > +   };
> > +
> > +   u32 vio_dbg1;
> > +};
> > +
> > +struct mtk_devapc_data {
> > +   u32 vio_idx_num;
> > +   u32 vio_mask_offset;
> > +   u32 vio_sta_offset;
> > +   u32 vio_dbg0_offset;
> > +   u32 vio_dbg1_offset;
> > +   u32 apc_con_offset;
> > +   u32 vio_shift_sta_offset;
> > +   u32 vio_shift_sel_offset;
> > +   u32 vio_shift_con_offset;
> > +};
> 
> Please describe the fields of the struct, that will make it easier to 
> understand 
> the driver.

Okay, I'll try to add more description about this struct. May be like:

struct mtk_devapc_data {
/* numbers of violation index */
u32 vio_idx_num;

/* reg offset */
u32 vio_mask_offset;
u32 vio_sta_offset;
u32 vio_dbg0_offset;
u32 vio_dbg1_offset;
u32 apc_con_offset;
u32 vio_shift_sta_offset;
u32 vio_shift_sel_offset;
u32 vio_shift_con_offset;
};

> 
> > +
> > +struct mtk_devapc_context {
> > +   struct device *dev;
> > +   void __iomem *infra_base;
> > +   struct clk *infra_clk

Re: [PATCH v7 2/2] soc: mediatek: add mt6779 devapc driver

2020-10-05 Thread Neal Liu
Hi Chun-Kuang,

On Sat, 2020-10-03 at 00:24 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月27日 週四 上午11:07寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> >  drivers/soc/mediatek/Kconfig  |9 ++
> >  drivers/soc/mediatek/Makefile |1 +
> >  drivers/soc/mediatek/mtk-devapc.c |  305 
> > +
> >  3 files changed, 315 insertions(+)
> >  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> >
> 
> [snip]
> 
> > +
> > +static int mtk_devapc_probe(struct platform_device *pdev)
> > +{
> > +   struct device_node *node = pdev->dev.of_node;
> > +   struct mtk_devapc_context *ctx;
> > +   u32 devapc_irq;
> > +   int ret;
> > +
> > +   if (IS_ERR(node))
> > +   return -ENODEV;
> > +
> > +   ctx = devm_kzalloc(>dev, sizeof(*ctx), GFP_KERNEL);
> > +   if (!ctx)
> > +   return -ENOMEM;
> > +
> > +   ctx->data = of_device_get_match_data(>dev);
> > +   ctx->dev = >dev;
> > +
> > +   ctx->infra_base = of_iomap(node, 0);
> > +   if (!ctx->infra_base)
> > +   return -EINVAL;
> > +
> > +   devapc_irq = irq_of_parse_and_map(node, 0);
> > +   if (!devapc_irq)
> > +   return -EINVAL;
> > +
> > +   ctx->infra_clk = devm_clk_get(>dev, "devapc-infra-clock");
> > +   if (IS_ERR(ctx->infra_clk))
> > +   return -EINVAL;
> > +
> > +   if (clk_prepare_enable(ctx->infra_clk))
> > +   return -EINVAL;
> 
> What would happen if you do not enable this clock? I think this
> hardware is already initialized in trust zone.
> 
> Regards,
> Chun-Kuang.

It cannot handle violation if the clock is disabled.
This parts of hardware is not initialized in TrustZone.

The another parts of hardware is initialized in TrustZone which is
responsible for permission control. I think that is the part what you
intend to express.

-Neal

> 
> > +
> > +   ret = devm_request_irq(>dev, devapc_irq,
> > +  (irq_handler_t)devapc_violation_irq,
> > +  IRQF_TRIGGER_NONE, "devapc", ctx);
> > +   if (ret) {
> > +   clk_disable_unprepare(ctx->infra_clk);
> > +   return ret;
> > +   }
> > +
> > +   platform_set_drvdata(pdev, ctx);
> > +
> > +   start_devapc(ctx);
> > +
> > +   return 0;
> > +}
> > +



Re: [PATCH v7] Add MediaTek MT6779 devapc driver

2020-09-30 Thread Neal Liu
Hi Matt,

Hope this mail could find you well.
Is everything okay?
It would be glad if you could reply me no matter the review status.

Thanks

-Neal

On Tue, 2020-09-22 at 15:13 +0800, Neal Liu wrote:
> Hi Matthias,
> 
> We need this driver supported on main-line.
> Could you save your time for us to review it?
> Thanks
> 
> -Neal
> 
> On Wed, 2020-09-16 at 16:58 +0800, Neal Liu wrote:
> > Hi Rob, Matthias, Chun-Kuang,
> > 
> > Sorry for pushing you so hard.
> > May I know is this patch set is comfortable to apply on latest kernel?
> > Thanks
> > 
> > -Neal
> > 
> > On Wed, 2020-09-09 at 16:37 +0800, Neal Liu wrote:
> > > Hi Rob, Matthias, Chun-Kuang,
> > > 
> > > Please kindly let me know your comments about this patch set.
> > > Thanks
> > > 
> > > -Neal
> > > 
> > > On Wed, 2020-09-02 at 14:40 +0800, Neal Liu wrote:
> > > > Hi Rob, Matthias, Chun-Kuang,
> > > > 
> > > > Gentle ping for this patch set.
> > > > Thanks
> > > > 
> > > > -Neal
> > > > 
> > > > On Thu, 2020-08-27 at 11:06 +0800, Neal Liu wrote:
> > > > > These patch series introduce a MediaTek MT6779 devapc driver.
> > > > > 
> > > > > MediaTek bus fabric provides TrustZone security support and data 
> > > > > protection to prevent slaves from being accessed by unexpected 
> > > > > masters.
> > > > > The security violation is logged and sent to the processor for 
> > > > > further analysis or countermeasures.
> > > > > 
> > > > > Any occurrence of security violation would raise an interrupt, and it 
> > > > > will be handled by mtk-devapc driver.
> > > > > The violation information is printed in order to find the murderer.
> > > > > 
> > > > > changes since v6:
> > > > > - remove unnecessary mask/unmask module irq during ISR.
> > > > > 
> > > > > changes since v5:
> > > > > - remove redundant write reg operation.
> > > > > - use static variable of vio_dbgs instead.
> > > > > - add stop_devapc() if driver is removed.
> > > > > 
> > > > > changes since v4:
> > > > > - refactor data structure.
> > > > > - merge two simple functions into one.
> > > > > - refactor register setting to prevent too many function call 
> > > > > overhead.
> > > > > 
> > > > > changes since v3:
> > > > > - revise violation handling flow to make it more easily to understand
> > > > >   hardware behavior.
> > > > > - add more comments to understand how hardware works.
> > > > > 
> > > > > changes since v2:
> > > > > - pass platform info through DT data.
> > > > > - remove unnecessary function.
> > > > > - remove slave_type because it always equals to 1 in current support 
> > > > > SoC.
> > > > > - use vio_idx_num instread of list all devices' index.
> > > > > - add more comments to describe hardware behavior.
> > > > > 
> > > > > changes since v1:
> > > > > - move SoC specific part to DT data.
> > > > > - remove unnecessary boundary check.
> > > > > - remove unnecessary data type declaration.
> > > > > - use read_poll_timeout() instread of for loop polling.
> > > > > - revise coding style elegantly.
> > > > > 
> > > > > 
> > > > > *** BLURB HERE ***
> > > > > 
> > > > > Neal Liu (2):
> > > > >   dt-bindings: devapc: add bindings for mtk-devapc
> > > > >   soc: mediatek: add mt6779 devapc driver
> > > > > 
> > > > >  .../bindings/soc/mediatek/devapc.yaml |  58 
> > > > >  drivers/soc/mediatek/Kconfig  |   9 +
> > > > >  drivers/soc/mediatek/Makefile |   1 +
> > > > >  drivers/soc/mediatek/mtk-devapc.c | 305 
> > > > > ++
> > > > >  4 files changed, 373 insertions(+)
> > > > >  create mode 100644 
> > > > > Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> > > > >  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> > > > > 
> > > > 
> > > > 
> > > 
> > > 
> > 
> > 
> 
> 



Re: [PATCH v7] Add MediaTek MT6779 devapc driver

2020-09-22 Thread Neal Liu
Hi Matthias,

We need this driver supported on main-line.
Could you save your time for us to review it?
Thanks

-Neal

On Wed, 2020-09-16 at 16:58 +0800, Neal Liu wrote:
> Hi Rob, Matthias, Chun-Kuang,
> 
> Sorry for pushing you so hard.
> May I know is this patch set is comfortable to apply on latest kernel?
> Thanks
> 
> -Neal
> 
> On Wed, 2020-09-09 at 16:37 +0800, Neal Liu wrote:
> > Hi Rob, Matthias, Chun-Kuang,
> > 
> > Please kindly let me know your comments about this patch set.
> > Thanks
> > 
> > -Neal
> > 
> > On Wed, 2020-09-02 at 14:40 +0800, Neal Liu wrote:
> > > Hi Rob, Matthias, Chun-Kuang,
> > > 
> > > Gentle ping for this patch set.
> > > Thanks
> > > 
> > > -Neal
> > > 
> > > On Thu, 2020-08-27 at 11:06 +0800, Neal Liu wrote:
> > > > These patch series introduce a MediaTek MT6779 devapc driver.
> > > > 
> > > > MediaTek bus fabric provides TrustZone security support and data 
> > > > protection to prevent slaves from being accessed by unexpected masters.
> > > > The security violation is logged and sent to the processor for further 
> > > > analysis or countermeasures.
> > > > 
> > > > Any occurrence of security violation would raise an interrupt, and it 
> > > > will be handled by mtk-devapc driver.
> > > > The violation information is printed in order to find the murderer.
> > > > 
> > > > changes since v6:
> > > > - remove unnecessary mask/unmask module irq during ISR.
> > > > 
> > > > changes since v5:
> > > > - remove redundant write reg operation.
> > > > - use static variable of vio_dbgs instead.
> > > > - add stop_devapc() if driver is removed.
> > > > 
> > > > changes since v4:
> > > > - refactor data structure.
> > > > - merge two simple functions into one.
> > > > - refactor register setting to prevent too many function call overhead.
> > > > 
> > > > changes since v3:
> > > > - revise violation handling flow to make it more easily to understand
> > > >   hardware behavior.
> > > > - add more comments to understand how hardware works.
> > > > 
> > > > changes since v2:
> > > > - pass platform info through DT data.
> > > > - remove unnecessary function.
> > > > - remove slave_type because it always equals to 1 in current support 
> > > > SoC.
> > > > - use vio_idx_num instread of list all devices' index.
> > > > - add more comments to describe hardware behavior.
> > > > 
> > > > changes since v1:
> > > > - move SoC specific part to DT data.
> > > > - remove unnecessary boundary check.
> > > > - remove unnecessary data type declaration.
> > > > - use read_poll_timeout() instread of for loop polling.
> > > > - revise coding style elegantly.
> > > > 
> > > > 
> > > > *** BLURB HERE ***
> > > > 
> > > > Neal Liu (2):
> > > >   dt-bindings: devapc: add bindings for mtk-devapc
> > > >   soc: mediatek: add mt6779 devapc driver
> > > > 
> > > >  .../bindings/soc/mediatek/devapc.yaml |  58 
> > > >  drivers/soc/mediatek/Kconfig  |   9 +
> > > >  drivers/soc/mediatek/Makefile |   1 +
> > > >  drivers/soc/mediatek/mtk-devapc.c | 305 ++
> > > >  4 files changed, 373 insertions(+)
> > > >  create mode 100644 
> > > > Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> > > >  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> > > > 
> > > 
> > > 
> > 
> > 
> 
> 



Re: [PATCH v7] Add MediaTek MT6779 devapc driver

2020-09-16 Thread Neal Liu
Hi Rob, Matthias, Chun-Kuang,

Sorry for pushing you so hard.
May I know is this patch set is comfortable to apply on latest kernel?
Thanks

-Neal

On Wed, 2020-09-09 at 16:37 +0800, Neal Liu wrote:
> Hi Rob, Matthias, Chun-Kuang,
> 
> Please kindly let me know your comments about this patch set.
> Thanks
> 
> -Neal
> 
> On Wed, 2020-09-02 at 14:40 +0800, Neal Liu wrote:
> > Hi Rob, Matthias, Chun-Kuang,
> > 
> > Gentle ping for this patch set.
> > Thanks
> > 
> > -Neal
> > 
> > On Thu, 2020-08-27 at 11:06 +0800, Neal Liu wrote:
> > > These patch series introduce a MediaTek MT6779 devapc driver.
> > > 
> > > MediaTek bus fabric provides TrustZone security support and data 
> > > protection to prevent slaves from being accessed by unexpected masters.
> > > The security violation is logged and sent to the processor for further 
> > > analysis or countermeasures.
> > > 
> > > Any occurrence of security violation would raise an interrupt, and it 
> > > will be handled by mtk-devapc driver.
> > > The violation information is printed in order to find the murderer.
> > > 
> > > changes since v6:
> > > - remove unnecessary mask/unmask module irq during ISR.
> > > 
> > > changes since v5:
> > > - remove redundant write reg operation.
> > > - use static variable of vio_dbgs instead.
> > > - add stop_devapc() if driver is removed.
> > > 
> > > changes since v4:
> > > - refactor data structure.
> > > - merge two simple functions into one.
> > > - refactor register setting to prevent too many function call overhead.
> > > 
> > > changes since v3:
> > > - revise violation handling flow to make it more easily to understand
> > >   hardware behavior.
> > > - add more comments to understand how hardware works.
> > > 
> > > changes since v2:
> > > - pass platform info through DT data.
> > > - remove unnecessary function.
> > > - remove slave_type because it always equals to 1 in current support SoC.
> > > - use vio_idx_num instread of list all devices' index.
> > > - add more comments to describe hardware behavior.
> > > 
> > > changes since v1:
> > > - move SoC specific part to DT data.
> > > - remove unnecessary boundary check.
> > > - remove unnecessary data type declaration.
> > > - use read_poll_timeout() instread of for loop polling.
> > > - revise coding style elegantly.
> > > 
> > > 
> > > *** BLURB HERE ***
> > > 
> > > Neal Liu (2):
> > >   dt-bindings: devapc: add bindings for mtk-devapc
> > >   soc: mediatek: add mt6779 devapc driver
> > > 
> > >  .../bindings/soc/mediatek/devapc.yaml |  58 
> > >  drivers/soc/mediatek/Kconfig  |   9 +
> > >  drivers/soc/mediatek/Makefile |   1 +
> > >  drivers/soc/mediatek/mtk-devapc.c | 305 ++
> > >  4 files changed, 373 insertions(+)
> > >  create mode 100644 
> > > Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> > >  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> > > 
> > 
> > 
> 
> 



Re: [PATCH v7] Add MediaTek MT6779 devapc driver

2020-09-09 Thread Neal Liu
Hi Rob, Matthias, Chun-Kuang,

Please kindly let me know your comments about this patch set.
Thanks

-Neal

On Wed, 2020-09-02 at 14:40 +0800, Neal Liu wrote:
> Hi Rob, Matthias, Chun-Kuang,
> 
> Gentle ping for this patch set.
> Thanks
> 
> -Neal
> 
> On Thu, 2020-08-27 at 11:06 +0800, Neal Liu wrote:
> > These patch series introduce a MediaTek MT6779 devapc driver.
> > 
> > MediaTek bus fabric provides TrustZone security support and data protection 
> > to prevent slaves from being accessed by unexpected masters.
> > The security violation is logged and sent to the processor for further 
> > analysis or countermeasures.
> > 
> > Any occurrence of security violation would raise an interrupt, and it will 
> > be handled by mtk-devapc driver.
> > The violation information is printed in order to find the murderer.
> > 
> > changes since v6:
> > - remove unnecessary mask/unmask module irq during ISR.
> > 
> > changes since v5:
> > - remove redundant write reg operation.
> > - use static variable of vio_dbgs instead.
> > - add stop_devapc() if driver is removed.
> > 
> > changes since v4:
> > - refactor data structure.
> > - merge two simple functions into one.
> > - refactor register setting to prevent too many function call overhead.
> > 
> > changes since v3:
> > - revise violation handling flow to make it more easily to understand
> >   hardware behavior.
> > - add more comments to understand how hardware works.
> > 
> > changes since v2:
> > - pass platform info through DT data.
> > - remove unnecessary function.
> > - remove slave_type because it always equals to 1 in current support SoC.
> > - use vio_idx_num instread of list all devices' index.
> > - add more comments to describe hardware behavior.
> > 
> > changes since v1:
> > - move SoC specific part to DT data.
> > - remove unnecessary boundary check.
> > - remove unnecessary data type declaration.
> > - use read_poll_timeout() instread of for loop polling.
> > - revise coding style elegantly.
> > 
> > 
> > *** BLURB HERE ***
> > 
> > Neal Liu (2):
> >   dt-bindings: devapc: add bindings for mtk-devapc
> >   soc: mediatek: add mt6779 devapc driver
> > 
> >  .../bindings/soc/mediatek/devapc.yaml |  58 
> >  drivers/soc/mediatek/Kconfig  |   9 +
> >  drivers/soc/mediatek/Makefile |   1 +
> >  drivers/soc/mediatek/mtk-devapc.c | 305 ++
> >  4 files changed, 373 insertions(+)
> >  create mode 100644 
> > Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> >  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> > 
> 
> 



Re: [PATCH v7] Add MediaTek MT6779 devapc driver

2020-09-02 Thread Neal Liu
Hi Rob, Matthias, Chun-Kuang,

Gentle ping for this patch set.
Thanks

-Neal

On Thu, 2020-08-27 at 11:06 +0800, Neal Liu wrote:
> These patch series introduce a MediaTek MT6779 devapc driver.
> 
> MediaTek bus fabric provides TrustZone security support and data protection 
> to prevent slaves from being accessed by unexpected masters.
> The security violation is logged and sent to the processor for further 
> analysis or countermeasures.
> 
> Any occurrence of security violation would raise an interrupt, and it will be 
> handled by mtk-devapc driver.
> The violation information is printed in order to find the murderer.
> 
> changes since v6:
> - remove unnecessary mask/unmask module irq during ISR.
> 
> changes since v5:
> - remove redundant write reg operation.
> - use static variable of vio_dbgs instead.
> - add stop_devapc() if driver is removed.
> 
> changes since v4:
> - refactor data structure.
> - merge two simple functions into one.
> - refactor register setting to prevent too many function call overhead.
> 
> changes since v3:
> - revise violation handling flow to make it more easily to understand
>   hardware behavior.
> - add more comments to understand how hardware works.
> 
> changes since v2:
> - pass platform info through DT data.
> - remove unnecessary function.
> - remove slave_type because it always equals to 1 in current support SoC.
> - use vio_idx_num instread of list all devices' index.
> - add more comments to describe hardware behavior.
> 
> changes since v1:
> - move SoC specific part to DT data.
> - remove unnecessary boundary check.
> - remove unnecessary data type declaration.
> - use read_poll_timeout() instread of for loop polling.
> - revise coding style elegantly.
> 
> 
> *** BLURB HERE ***
> 
> Neal Liu (2):
>   dt-bindings: devapc: add bindings for mtk-devapc
>   soc: mediatek: add mt6779 devapc driver
> 
>  .../bindings/soc/mediatek/devapc.yaml |  58 
>  drivers/soc/mediatek/Kconfig  |   9 +
>  drivers/soc/mediatek/Makefile |   1 +
>  drivers/soc/mediatek/mtk-devapc.c | 305 ++
>  4 files changed, 373 insertions(+)
>  create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
>  create mode 100644 drivers/soc/mediatek/mtk-devapc.c
> 



[PATCH v7 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-26 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 ++
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  305 +
 3 files changed, 315 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..0ba61d7
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,305 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#define VIO_MOD_TO_REG_IND(m)  ((m) / 32)
+#define VIO_MOD_TO_REG_OFF(m)  ((m) % 32)
+
+struct mtk_devapc_vio_dbgs {
+   union {
+   u32 vio_dbg0;
+   struct {
+   u32 mstid:16;
+   u32 dmnid:6;
+   u32 vio_w:1;
+   u32 vio_r:1;
+   u32 addr_h:4;
+   u32 resv:4;
+   } dbg0_bits;
+   };
+
+   u32 vio_dbg1;
+};
+
+struct mtk_devapc_data {
+   u32 vio_idx_num;
+   u32 vio_mask_offset;
+   u32 vio_sta_offset;
+   u32 vio_dbg0_offset;
+   u32 vio_dbg1_offset;
+   u32 apc_con_offset;
+   u32 vio_shift_sta_offset;
+   u32 vio_shift_sel_offset;
+   u32 vio_shift_con_offset;
+};
+
+struct mtk_devapc_context {
+   struct device *dev;
+   void __iomem *infra_base;
+   struct clk *infra_clk;
+   const struct mtk_devapc_data *data;
+};
+
+static void clear_vio_status(struct mtk_devapc_context *ctx)
+{
+   void __iomem *reg;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_sta_offset;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num - 1); i++)
+   writel(GENMASK(31, 0), reg + 4 * i);
+
+   writel(GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1), 0),
+  reg + 4 * i);
+}
+
+static void mask_module_irq(struct mtk_devapc_context *ctx, bool mask)
+{
+   void __iomem *reg;
+   u32 val;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_mask_offset;
+
+   if (mask)
+   val = GENMASK(31, 0);
+   else
+   val = 0;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num - 1); i++)
+   writel(val, reg + 4 * i);
+
+   val = readl(reg + 4 * i);
+   if (mask)
+   val |= GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1),
+  0);
+   else
+   val &= ~GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1),
+   0);
+
+   writel(val, reg + 4 * i);
+}
+
+#define PHY_DEVAPC_TIMEOUT 0x1
+
+/*
+ * devapc_sync_vio_dbg - do "shift" mechansim" to get full violation 
information.
+ *   shift mechanism is depends on devapc hardware design.
+ *   Mediatek devapc set multiple slaves as a group.
+ *   When violation is triggered, violation info is kept
+ *   inside devapc hardware.
+ *   Driver should do shift mechansim to sync full 
violation
+

[PATCH v7] Add MediaTek MT6779 devapc driver

2020-08-26 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further analysis 
or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v6:
- remove unnecessary mask/unmask module irq during ISR.

changes since v5:
- remove redundant write reg operation.
- use static variable of vio_dbgs instead.
- add stop_devapc() if driver is removed.

changes since v4:
- refactor data structure.
- merge two simple functions into one.
- refactor register setting to prevent too many function call overhead.

changes since v3:
- revise violation handling flow to make it more easily to understand
  hardware behavior.
- add more comments to understand how hardware works.

changes since v2:
- pass platform info through DT data.
- remove unnecessary function.
- remove slave_type because it always equals to 1 in current support SoC.
- use vio_idx_num instread of list all devices' index.
- add more comments to describe hardware behavior.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mt6779 devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  58 
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 305 ++
 4 files changed, 373 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

-- 
2.18.0


[PATCH v7 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-08-26 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..6c763f8
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


Re: [PATCH v6 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-26 Thread Neal Liu
Hi Chun-Kuang,

On Tue, 2020-08-18 at 14:20 +0800, Neal Liu wrote:
> Hi Chun-Kuang,
> 
> On Tue, 2020-08-18 at 10:44 +0800, Neal Liu wrote:
> > Hi Chun-Kuang,
> > 
> > On Mon, 2020-08-17 at 23:13 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > > 
> > > Neal Liu  於 2020年8月17日 週一 下午12:02寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > On Sat, 2020-08-15 at 11:03 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年8月13日 週四 上午11:33寫道:
> > > > > >
> > > > > > MediaTek bus fabric provides TrustZone security support and data
> > > > > > protection to prevent slaves from being accessed by unexpected
> > > > > > masters.
> > > > > > The security violation is logged and sent to the processor for
> > > > > > further analysis or countermeasures.
> > > > > >
> > > > > > Any occurrence of security violation would raise an interrupt, and
> > > > > > it will be handled by mtk-devapc driver. The violation
> > > > > > information is printed in order to find the murderer.
> > > > > >
> > > > > > Signed-off-by: Neal Liu 
> > > > > > ---
> > > > >
> > > > > [snip]
> > > > >
> > > > > > +/*
> > > > > > + * devapc_violation_irq - the devapc Interrupt Service Routine 
> > > > > > (ISR) will dump
> > > > > > + *violation information including which 
> > > > > > master violates
> > > > > > + *access slave.
> > > > > > + */
> > > > > > +static irqreturn_t devapc_violation_irq(int irq_number,
> > > > > > +   struct mtk_devapc_context 
> > > > > > *ctx)
> > > > > > +{
> > > > > > +   /*
> > > > > > +* Mask slave's irq before clearing vio status.
> > > > > > +* Must do it to avoid nested interrupt and prevent
> > > > > > +* unexpected behavior.
> > > > > > +*/
> > > > > > +   mask_module_irq(ctx, true);
> > > > >
> > > > > I still don't understand why nested interrupt happen. If two CPU
> > > > > process different devapc interrupt at the same time, mask interrupt
> > > > > could not prevent these two CPU to sync vio dbg at the same time. As I
> > > > > know, in ARM CPU, only CPU0 process irq handler, and all devapc
> > > > > interrupt has the same priority, so why nested interrupt happen? Could
> > > > > you explain more detail about how nested interrupt happen?
> > > >
> > > > If there is another violation happened before previous violation is
> > > > fully handled, nested interrupt would happen.
> > > >
> > > > Let's me take an example:
> > > > vio A happen
> > > > enter A ISR
> > > > ... vio B happen
> > > > finish A ISRenter B ISR
> > > > ...
> > > > finish B ISR
> > > >
> > > > We mask all module's irq to avoid nested interrupt.
> > > 
> > > This is not 'nested' interrupt. After A ISR is finished, B ISR happen.
> > > So A ISR and B ISR are consecutive interrupt, not nested interrupt.
> > > To compare mask irq and no mask irq, Let's consider this situation:
> > > 
> > > 1. 1000 consecutive violation happen, the time period between two
> > > violation is 0.01 ms, so the total time is 10ms. (In 10ms, 1000
> > > violation happen)
> > > 2. One ISR handle time is 1 ms, so in one ISR handler, 100 violation 
> > > happen.
> > > 
> > > For mask irq solution, 10 ISR handler is trigger. For no mask irq
> > > solution, 11 ISR handler is trigger.
> > > I think these two solution have similar result, and no mask irq
> > > solution print more information (If these 1000 violation is trigger by
> > > 20 different driver, no mask solution may show one more driver than
> > > mask solution)
> > > So I think it's not necessary to mask irq in irq handler.
> > > 
> > 
> > No, my example is B ISR is entered before A ISR finished.
> > Why this is not nested?
> > vio A happen
> 

Re: [PATCH v6 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-18 Thread Neal Liu
Hi Chun-Kuang,

On Tue, 2020-08-18 at 10:44 +0800, Neal Liu wrote:
> Hi Chun-Kuang,
> 
> On Mon, 2020-08-17 at 23:13 +0800, Chun-Kuang Hu wrote:
> > Hi, Neal:
> > 
> > Neal Liu  於 2020年8月17日 週一 下午12:02寫道:
> > >
> > > Hi Chun-Kuang,
> > >
> > > On Sat, 2020-08-15 at 11:03 +0800, Chun-Kuang Hu wrote:
> > > > Hi, Neal:
> > > >
> > > > Neal Liu  於 2020年8月13日 週四 上午11:33寫道:
> > > > >
> > > > > MediaTek bus fabric provides TrustZone security support and data
> > > > > protection to prevent slaves from being accessed by unexpected
> > > > > masters.
> > > > > The security violation is logged and sent to the processor for
> > > > > further analysis or countermeasures.
> > > > >
> > > > > Any occurrence of security violation would raise an interrupt, and
> > > > > it will be handled by mtk-devapc driver. The violation
> > > > > information is printed in order to find the murderer.
> > > > >
> > > > > Signed-off-by: Neal Liu 
> > > > > ---
> > > >
> > > > [snip]
> > > >
> > > > > +/*
> > > > > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) 
> > > > > will dump
> > > > > + *violation information including which 
> > > > > master violates
> > > > > + *access slave.
> > > > > + */
> > > > > +static irqreturn_t devapc_violation_irq(int irq_number,
> > > > > +   struct mtk_devapc_context 
> > > > > *ctx)
> > > > > +{
> > > > > +   /*
> > > > > +* Mask slave's irq before clearing vio status.
> > > > > +* Must do it to avoid nested interrupt and prevent
> > > > > +* unexpected behavior.
> > > > > +*/
> > > > > +   mask_module_irq(ctx, true);
> > > >
> > > > I still don't understand why nested interrupt happen. If two CPU
> > > > process different devapc interrupt at the same time, mask interrupt
> > > > could not prevent these two CPU to sync vio dbg at the same time. As I
> > > > know, in ARM CPU, only CPU0 process irq handler, and all devapc
> > > > interrupt has the same priority, so why nested interrupt happen? Could
> > > > you explain more detail about how nested interrupt happen?
> > >
> > > If there is another violation happened before previous violation is
> > > fully handled, nested interrupt would happen.
> > >
> > > Let's me take an example:
> > > vio A happen
> > > enter A ISR
> > > ... vio B happen
> > > finish A ISRenter B ISR
> > > ...
> > > finish B ISR
> > >
> > > We mask all module's irq to avoid nested interrupt.
> > 
> > This is not 'nested' interrupt. After A ISR is finished, B ISR happen.
> > So A ISR and B ISR are consecutive interrupt, not nested interrupt.
> > To compare mask irq and no mask irq, Let's consider this situation:
> > 
> > 1. 1000 consecutive violation happen, the time period between two
> > violation is 0.01 ms, so the total time is 10ms. (In 10ms, 1000
> > violation happen)
> > 2. One ISR handle time is 1 ms, so in one ISR handler, 100 violation happen.
> > 
> > For mask irq solution, 10 ISR handler is trigger. For no mask irq
> > solution, 11 ISR handler is trigger.
> > I think these two solution have similar result, and no mask irq
> > solution print more information (If these 1000 violation is trigger by
> > 20 different driver, no mask solution may show one more driver than
> > mask solution)
> > So I think it's not necessary to mask irq in irq handler.
> > 
> 
> No, my example is B ISR is entered before A ISR finished.
> Why this is not nested?
> vio A happen
> enter A ISR
> ... vio B happen
> ...   enter B ISR
> finish A ISR
> ...
>   ...
> finish B ISR
> 

I have some misunderstanding about how ARM CPU & GIC works. I'll confirm
it and get back to you. Please ignore previous mail thread.
Thanks !

> > >
> > > >
> > > > > +
> > > > > +   while (devapc_sync_vio_dbg(ctx))
> > > > > +   devapc_extract_vio_dbg(ctx);
> 

Re: [PATCH v6 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-17 Thread Neal Liu
Hi Chun-Kuang,

On Mon, 2020-08-17 at 23:13 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月17日 週一 下午12:02寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Sat, 2020-08-15 at 11:03 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年8月13日 週四 上午11:33寫道:
> > > >
> > > > MediaTek bus fabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violation is logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by mtk-devapc driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > > > ---
> > >
> > > [snip]
> > >
> > > > +/*
> > > > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) 
> > > > will dump
> > > > + *violation information including which master 
> > > > violates
> > > > + *access slave.
> > > > + */
> > > > +static irqreturn_t devapc_violation_irq(int irq_number,
> > > > +   struct mtk_devapc_context *ctx)
> > > > +{
> > > > +   /*
> > > > +* Mask slave's irq before clearing vio status.
> > > > +* Must do it to avoid nested interrupt and prevent
> > > > +* unexpected behavior.
> > > > +*/
> > > > +   mask_module_irq(ctx, true);
> > >
> > > I still don't understand why nested interrupt happen. If two CPU
> > > process different devapc interrupt at the same time, mask interrupt
> > > could not prevent these two CPU to sync vio dbg at the same time. As I
> > > know, in ARM CPU, only CPU0 process irq handler, and all devapc
> > > interrupt has the same priority, so why nested interrupt happen? Could
> > > you explain more detail about how nested interrupt happen?
> >
> > If there is another violation happened before previous violation is
> > fully handled, nested interrupt would happen.
> >
> > Let's me take an example:
> > vio A happen
> > enter A ISR
> > ... vio B happen
> > finish A ISRenter B ISR
> > ...
> > finish B ISR
> >
> > We mask all module's irq to avoid nested interrupt.
> 
> This is not 'nested' interrupt. After A ISR is finished, B ISR happen.
> So A ISR and B ISR are consecutive interrupt, not nested interrupt.
> To compare mask irq and no mask irq, Let's consider this situation:
> 
> 1. 1000 consecutive violation happen, the time period between two
> violation is 0.01 ms, so the total time is 10ms. (In 10ms, 1000
> violation happen)
> 2. One ISR handle time is 1 ms, so in one ISR handler, 100 violation happen.
> 
> For mask irq solution, 10 ISR handler is trigger. For no mask irq
> solution, 11 ISR handler is trigger.
> I think these two solution have similar result, and no mask irq
> solution print more information (If these 1000 violation is trigger by
> 20 different driver, no mask solution may show one more driver than
> mask solution)
> So I think it's not necessary to mask irq in irq handler.
> 

No, my example is B ISR is entered before A ISR finished.
Why this is not nested?
vio A happen
enter A ISR
... vio B happen
... enter B ISR
finish A ISR
...
...
finish B ISR

> >
> > >
> > > > +
> > > > +   while (devapc_sync_vio_dbg(ctx))
> > > > +   devapc_extract_vio_dbg(ctx);
> > > > +
> > > > +   /*
> > > > +* Ensure that violation info are written
> > > > +* before further operations
> > > > +*/
> > > > +   smp_mb();
> > > > +
> > > > +   clear_vio_status(ctx);
> > > > +   mask_module_irq(ctx, false);
> > > > +
> > > > +   return IRQ_HANDLED;
> > > > +}
> > > > +
> > >
> > > [snip]
> > >
> > > > +
> > > > +static int mtk_devapc_remove(struct platform_device *pdev)
> > > > +{
> > > > +   struct mtk_devapc_context *ctx = platform_ge

Re: [PATCH v6 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-16 Thread Neal Liu
Hi Chun-Kuang,

On Sat, 2020-08-15 at 11:03 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月13日 週四 上午11:33寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +/*
> > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) will 
> > dump
> > + *violation information including which master 
> > violates
> > + *access slave.
> > + */
> > +static irqreturn_t devapc_violation_irq(int irq_number,
> > +   struct mtk_devapc_context *ctx)
> > +{
> > +   /*
> > +* Mask slave's irq before clearing vio status.
> > +* Must do it to avoid nested interrupt and prevent
> > +* unexpected behavior.
> > +*/
> > +   mask_module_irq(ctx, true);
> 
> I still don't understand why nested interrupt happen. If two CPU
> process different devapc interrupt at the same time, mask interrupt
> could not prevent these two CPU to sync vio dbg at the same time. As I
> know, in ARM CPU, only CPU0 process irq handler, and all devapc
> interrupt has the same priority, so why nested interrupt happen? Could
> you explain more detail about how nested interrupt happen?

If there is another violation happened before previous violation is
fully handled, nested interrupt would happen.

Let's me take an example:
vio A happen
enter A ISR
... vio B happen
finish A ISRenter B ISR
...
finish B ISR

We mask all module's irq to avoid nested interrupt.

> 
> > +
> > +   while (devapc_sync_vio_dbg(ctx))
> > +   devapc_extract_vio_dbg(ctx);
> > +
> > +   /*
> > +* Ensure that violation info are written
> > +* before further operations
> > +*/
> > +   smp_mb();
> > +
> > +   clear_vio_status(ctx);
> > +   mask_module_irq(ctx, false);
> > +
> > +   return IRQ_HANDLED;
> > +}
> > +
> 
> [snip]
> 
> > +
> > +static int mtk_devapc_remove(struct platform_device *pdev)
> > +{
> > +   struct mtk_devapc_context *ctx = platform_get_drvdata(pdev);
> > +
> > +   stop_devapc(ctx);
> > +
> > +   if (ctx->infra_clk)
> 
> This always true.

Does it mean that remove function would be called only if probe function
is returned successfully?
Is there any chance this function would be called directly?

> 
> Regards,
> Chun-Kuang.
> 
> > +   clk_disable_unprepare(ctx->infra_clk);
> > +
> > +   return 0;
> > +}
> > +
> > +static struct platform_driver mtk_devapc_driver = {
> > +   .probe = mtk_devapc_probe,
> > +   .remove = mtk_devapc_remove,
> > +   .driver = {
> > +   .name = KBUILD_MODNAME,
> > +   .of_match_table = mtk_devapc_dt_match,
> > +   },
> > +};
> > +
> > +module_platform_driver(mtk_devapc_driver);
> > +
> > +MODULE_DESCRIPTION("Mediatek Device APC Driver");
> > +MODULE_AUTHOR("Neal Liu ");
> > +MODULE_LICENSE("GPL");
> > --
> > 1.7.9.5
> > ___
> > Linux-mediatek mailing list
> > linux-media...@lists.infradead.org
> > http://lists.infradead.org/mailman/listinfo/linux-mediatek



[PATCH v6] Add MediaTek MT6779 devapc driver

2020-08-12 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further analysis 
or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v5:
- remove redundant write reg operation.
- use static variable of vio_dbgs instead.
- add stop_devapc() if driver is removed.

changes since v4:
- refactor data structure.
- merge two simple functions into one.
- refactor register setting to prevent too many function call overhead.

changes since v3:
- revise violation handling flow to make it more easily to understand
  hardware behavior.
- add more comments to understand how hardware works.

changes since v2:
- pass platform info through DT data.
- remove unnecessary function.
- remove slave_type because it always equals to 1 in current support SoC.
- use vio_idx_num instread of list all devices' index.
- add more comments to describe hardware behavior.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mt6779 devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  58 
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 320 ++
 4 files changed, 388 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

-- 
2.18.0


[PATCH v6 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-12 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 ++
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  320 +
 3 files changed, 330 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..5189b3f
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,320 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#define VIO_MOD_TO_REG_IND(m)  ((m) / 32)
+#define VIO_MOD_TO_REG_OFF(m)  ((m) % 32)
+
+struct mtk_devapc_vio_dbgs {
+   union {
+   u32 vio_dbg0;
+   struct {
+   u32 mstid:16;
+   u32 dmnid:6;
+   u32 vio_w:1;
+   u32 vio_r:1;
+   u32 addr_h:4;
+   u32 resv:4;
+   } dbg0_bits;
+   };
+
+   u32 vio_dbg1;
+};
+
+struct mtk_devapc_data {
+   u32 vio_idx_num;
+   u32 vio_mask_offset;
+   u32 vio_sta_offset;
+   u32 vio_dbg0_offset;
+   u32 vio_dbg1_offset;
+   u32 apc_con_offset;
+   u32 vio_shift_sta_offset;
+   u32 vio_shift_sel_offset;
+   u32 vio_shift_con_offset;
+};
+
+struct mtk_devapc_context {
+   struct device *dev;
+   void __iomem *infra_base;
+   struct clk *infra_clk;
+   const struct mtk_devapc_data *data;
+};
+
+static void clear_vio_status(struct mtk_devapc_context *ctx)
+{
+   void __iomem *reg;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_sta_offset;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num - 1); i++)
+   writel(GENMASK(31, 0), reg + 4 * i);
+
+   writel(GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1), 0),
+  reg + 4 * i);
+}
+
+static void mask_module_irq(struct mtk_devapc_context *ctx, bool mask)
+{
+   void __iomem *reg;
+   u32 val;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_mask_offset;
+
+   if (mask)
+   val = GENMASK(31, 0);
+   else
+   val = 0;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num - 1); i++)
+   writel(val, reg + 4 * i);
+
+   val = readl(reg + 4 * i);
+   if (mask)
+   val |= GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1),
+  0);
+   else
+   val &= ~GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1),
+   0);
+
+   writel(val, reg + 4 * i);
+}
+
+#define PHY_DEVAPC_TIMEOUT 0x1
+
+/*
+ * devapc_sync_vio_dbg - do "shift" mechansim" to get full violation 
information.
+ *   shift mechanism is depends on devapc hardware design.
+ *   Mediatek devapc set multiple slaves as a group.
+ *   When violation is triggered, violation info is kept
+ *   inside devapc hardware.
+ *   Driver should do shift mechansim to sync full 
violation
+

[PATCH v6 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-08-12 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..6c763f8
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


Re: [PATCH v5 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-10 Thread Neal Liu
Hi Chun-Kuang,

On Tue, 2020-08-11 at 07:14 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月10日 週一 上午11:43寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Fri, 2020-08-07 at 23:52 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年8月7日 週五 上午10:34寫道:
> > > >
> > > > MediaTek bus fabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violation is logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by mtk-devapc driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > > > ---
> > >
> > > [snip]
> > >
> > > > +
> > > > +#define PHY_DEVAPC_TIMEOUT 0x1
> > > > +
> > > > +/*
> > > > + * devapc_sync_vio_dbg - do "shift" mechansim" to get full violation 
> > > > information.
> > > > + *   shift mechanism is depends on devapc hardware 
> > > > design.
> > > > + *   Mediatek devapc set multiple slaves as a 
> > > > group.
> > > > + *   When violation is triggered, violation info 
> > > > is kept
> > > > + *   inside devapc hardware.
> > > > + *   Driver should do shift mechansim to sync full 
> > > > violation
> > > > + *   info to VIO_DBGs registers.
> > > > + *
> > > > + */
> > > > +static int devapc_sync_vio_dbg(struct mtk_devapc_context *ctx)
> > > > +{
> > > > +   void __iomem *pd_vio_shift_sta_reg;
> > > > +   void __iomem *pd_vio_shift_sel_reg;
> > > > +   void __iomem *pd_vio_shift_con_reg;
> > > > +   int min_shift_group;
> > > > +   int ret;
> > > > +   u32 val;
> > > > +
> > > > +   pd_vio_shift_sta_reg = ctx->infra_base +
> > > > +  ctx->data->vio_shift_sta_offset;
> > > > +   pd_vio_shift_sel_reg = ctx->infra_base +
> > > > +  ctx->data->vio_shift_sel_offset;
> > > > +   pd_vio_shift_con_reg = ctx->infra_base +
> > > > +  ctx->data->vio_shift_con_offset;
> > > > +
> > > > +   /* Find the minimum shift group which has violation */
> > > > +   val = readl(pd_vio_shift_sta_reg);
> > > > +   if (!val)
> > > > +   return false;
> > > > +
> > > > +   min_shift_group = __ffs(val);
> > > > +
> > > > +   /* Assign the group to sync */
> > > > +   writel(0x1 << min_shift_group, pd_vio_shift_sel_reg);
> > > > +
> > > > +   /* Start syncing */
> > > > +   writel(0x1, pd_vio_shift_con_reg);
> > > > +
> > > > +   ret = readl_poll_timeout(pd_vio_shift_con_reg, val, val == 0x3, 
> > > > 0,
> > > > +PHY_DEVAPC_TIMEOUT);
> > > > +   if (ret) {
> > > > +   dev_err(ctx->dev, "%s: Shift violation info failed\n", 
> > > > __func__);
> > > > +   return false;
> > > > +   }
> > > > +
> > > > +   /* Stop syncing */
> > > > +   writel(0x0, pd_vio_shift_con_reg);
> > > > +   writel(0x0, pd_vio_shift_sel_reg);
> > >
> > > This is redundant because you set this register before start syncing.
> >
> > No, we don't set this reg before start syncing.
> >
> 
> I'm talking about pd_vio_shift_sel_reg, and I find this before start syncing:
> 
>/* Assign the group to sync */
>writel(0x1 << min_shift_group, pd_vio_shift_sel_reg);
> 
>/* Start syncing */
>writel(0x1, pd_vio_shift_con_reg);
> 

We set 0 to make sure all bits are cleared. But it won't cause any
problem if we remove it. I'll update on next patch.
Thanks !

> > >
> > > > +   writel(0x1 << min_shift_group, pd_vio_shift_sta_reg);
> > >
> > &g

Re: [PATCH v5 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-09 Thread Neal Liu
Hi Chun-Kuang,

On Fri, 2020-08-07 at 23:52 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月7日 週五 上午10:34寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +#define PHY_DEVAPC_TIMEOUT 0x1
> > +
> > +/*
> > + * devapc_sync_vio_dbg - do "shift" mechansim" to get full violation 
> > information.
> > + *   shift mechanism is depends on devapc hardware 
> > design.
> > + *   Mediatek devapc set multiple slaves as a group.
> > + *   When violation is triggered, violation info is 
> > kept
> > + *   inside devapc hardware.
> > + *   Driver should do shift mechansim to sync full 
> > violation
> > + *   info to VIO_DBGs registers.
> > + *
> > + */
> > +static int devapc_sync_vio_dbg(struct mtk_devapc_context *ctx)
> > +{
> > +   void __iomem *pd_vio_shift_sta_reg;
> > +   void __iomem *pd_vio_shift_sel_reg;
> > +   void __iomem *pd_vio_shift_con_reg;
> > +   int min_shift_group;
> > +   int ret;
> > +   u32 val;
> > +
> > +   pd_vio_shift_sta_reg = ctx->infra_base +
> > +  ctx->data->vio_shift_sta_offset;
> > +   pd_vio_shift_sel_reg = ctx->infra_base +
> > +  ctx->data->vio_shift_sel_offset;
> > +   pd_vio_shift_con_reg = ctx->infra_base +
> > +  ctx->data->vio_shift_con_offset;
> > +
> > +   /* Find the minimum shift group which has violation */
> > +   val = readl(pd_vio_shift_sta_reg);
> > +   if (!val)
> > +   return false;
> > +
> > +   min_shift_group = __ffs(val);
> > +
> > +   /* Assign the group to sync */
> > +   writel(0x1 << min_shift_group, pd_vio_shift_sel_reg);
> > +
> > +   /* Start syncing */
> > +   writel(0x1, pd_vio_shift_con_reg);
> > +
> > +   ret = readl_poll_timeout(pd_vio_shift_con_reg, val, val == 0x3, 0,
> > +PHY_DEVAPC_TIMEOUT);
> > +   if (ret) {
> > +   dev_err(ctx->dev, "%s: Shift violation info failed\n", 
> > __func__);
> > +   return false;
> > +   }
> > +
> > +   /* Stop syncing */
> > +   writel(0x0, pd_vio_shift_con_reg);
> > +   writel(0x0, pd_vio_shift_sel_reg);
> 
> This is redundant because you set this register before start syncing.

No, we don't set this reg before start syncing.

> 
> > +   writel(0x1 << min_shift_group, pd_vio_shift_sta_reg);
> 
> You read this register to find minimum shift group, but you write it
> back into this register, so this function would get the same minimum
> shift group in next time, isn't it?

No. The operation means write clear. We won't get the same minimum shift
group after clear this bit.

> 
> > +
> > +   return true;
> > +}
> > +
> > +/*
> > + * devapc_extract_vio_dbg - extract full violation information after doing
> > + *  shift mechanism.
> > + */
> > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > +{
> > +   struct mtk_devapc_vio_dbgs *vio_dbgs;
> 
> struct mtk_devapc_vio_dbgs vio_dbgs;
> 
> Use stack instead of allocating from heap.

Why it cannot use heap if the memory is handled correctly?

> 
> > +   void __iomem *vio_dbg0_reg;
> > +   void __iomem *vio_dbg1_reg;
> > +
> > +   vio_dbgs = devm_kzalloc(ctx->dev, sizeof(struct 
> > mtk_devapc_vio_dbgs),
> > +   GFP_KERNEL);
> > +   if (!vio_dbgs)
> > +   return;
> > +
> > +   vio_dbg0_reg = ctx->infra_base + ctx->data->vio_dbg0_offset;
> > +   vio_dbg1_reg = ctx->infra_base + ctx->data->vio_dbg1_offset;
> > +
> > +   vio_dbgs->vio_dbg0 = readl(vio_dbg0_reg);
> > +   vio_dbgs->vio_dbg

[PATCH v5 2/2] soc: mediatek: add mt6779 devapc driver

2020-08-06 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 ++
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  315 +
 3 files changed, 325 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..73287cf
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,315 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#define VIO_MOD_TO_REG_IND(m)  ((m) / 32)
+#define VIO_MOD_TO_REG_OFF(m)  ((m) % 32)
+
+struct mtk_devapc_vio_dbgs {
+   union {
+   u32 vio_dbg0;
+   struct {
+   u32 mstid:16;
+   u32 dmnid:6;
+   u32 vio_w:1;
+   u32 vio_r:1;
+   u32 addr_h:4;
+   u32 resv:4;
+   } dbg0_bits;
+   };
+
+   u32 vio_dbg1;
+};
+
+struct mtk_devapc_data {
+   u32 vio_idx_num;
+   u32 vio_mask_offset;
+   u32 vio_sta_offset;
+   u32 vio_dbg0_offset;
+   u32 vio_dbg1_offset;
+   u32 apc_con_offset;
+   u32 vio_shift_sta_offset;
+   u32 vio_shift_sel_offset;
+   u32 vio_shift_con_offset;
+};
+
+struct mtk_devapc_context {
+   struct device *dev;
+   void __iomem *infra_base;
+   struct clk *infra_clk;
+   const struct mtk_devapc_data *data;
+};
+
+static void clear_vio_status(struct mtk_devapc_context *ctx)
+{
+   void __iomem *reg;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_sta_offset;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num - 1); i++)
+   writel(GENMASK(31, 0), reg + 4 * i);
+
+   writel(GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1), 0),
+  reg + 4 * i);
+}
+
+static void mask_module_irq(struct mtk_devapc_context *ctx, bool mask)
+{
+   void __iomem *reg;
+   u32 val;
+   int i;
+
+   reg = ctx->infra_base + ctx->data->vio_mask_offset;
+
+   if (mask)
+   val = GENMASK(31, 0);
+   else
+   val = 0;
+
+   for (i = 0; i < VIO_MOD_TO_REG_IND(ctx->data->vio_idx_num - 1); i++)
+   writel(val, reg + 4 * i);
+
+   val = readl(reg + 4 * i);
+   if (mask)
+   val |= GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1),
+0);
+   else
+   val &= ~GENMASK(VIO_MOD_TO_REG_OFF(ctx->data->vio_idx_num - 1),
+0);
+
+   writel(val, reg + 4 * i);
+}
+
+#define PHY_DEVAPC_TIMEOUT 0x1
+
+/*
+ * devapc_sync_vio_dbg - do "shift" mechansim" to get full violation 
information.
+ *   shift mechanism is depends on devapc hardware design.
+ *   Mediatek devapc set multiple slaves as a group.
+ *   When violation is triggered, violation info is kept
+ *   inside devapc hardware.
+ *   Driver should do

[PATCH v5 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-08-06 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..6c763f8
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


[PATCH v5] Add MediaTek MT6779 devapc driver

2020-08-06 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further analysis 
or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v4:
- refactor data structure.
- merge two simple functions into one.
- refactor register setting to prevent too many function call overhead.

changes since v3:
- revise violation handling flow to make it more easily to understand
  hardware behavior.
- add more comments to understand how hardware works.

changes since v2:
- pass platform info through DT data.
- remove unnecessary function.
- remove slave_type because it always equals to 1 in current support SoC.
- use vio_idx_num instread of list all devices' index.
- add more comments to describe hardware behavior.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mt6779 devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  58 
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 315 ++
 4 files changed, 383 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c

-- 
2.18.0


Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-08-03 Thread Neal Liu

On Tue, 2020-08-04 at 00:13 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月3日 週一 上午11:32寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Fri, 2020-07-31 at 23:03 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月31日 週五 上午10:44寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > >
> > > > On Thu, 2020-07-30 at 00:38 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> > > > > >
> > > > > > MediaTek bus fabric provides TrustZone security support and data
> > > > > > protection to prevent slaves from being accessed by unexpected
> > > > > > masters.
> > > > > > The security violation is logged and sent to the processor for
> > > > > > further analysis or countermeasures.
> > > > > >
> > > > > > Any occurrence of security violation would raise an interrupt, and
> > > > > > it will be handled by mtk-devapc driver. The violation
> > > > > > information is printed in order to find the murderer.
> > > > > >
> > > > > > Signed-off-by: Neal Liu 
> > > > > > ---
> > > > >
> > > > > [snip]
> > > > >
> > > > > > +
> > > > > > +/*
> > > > > > + * devapc_extract_vio_dbg - extract full violation information 
> > > > > > after doing
> > > > > > + *  shift mechanism.
> > > > > > + */
> > > > > > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > > > > > +{
> > > > > > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > > > > > +   struct mtk_devapc_vio_info *vio_info;
> > > > > > +   void __iomem *vio_dbg0_reg;
> > > > > > +   void __iomem *vio_dbg1_reg;
> > > > > > +   u32 dbg0;
> > > > > > +
> > > > > > +   vio_dbg0_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg0;
> > > > > > +   vio_dbg1_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg1;
> > > > > > +
> > > > > > +   vio_dbgs = ctx->vio_dbgs;
> > > > > > +   vio_info = ctx->vio_info;
> > > > > > +
> > > > > > +   /* Starts to extract violation information */
> > > > > > +   dbg0 = readl(vio_dbg0_reg);
> > > > > > +   vio_info->vio_addr = readl(vio_dbg1_reg);
> > > > > > +
> > > > > > +   vio_info->master_id = (dbg0 & vio_dbgs->mstid.mask) >>
> > > > > > + vio_dbgs->mstid.start;
> > > > >
> > > > > What is master_id? How could we use it to debug? For example, if we
> > > > > get a master_id = 1, what should we do for this?
> > > > >
> > > > > > +   vio_info->domain_id = (dbg0 & vio_dbgs->dmnid.mask) >>
> > > > > > + vio_dbgs->dmnid.start;
> > > > >
> > > > > What is domain_id? How could we use it to debug? For example, if we
> > > > > get a domain_id = 2, what should we do for this?
> > > > >
> > > >
> > > > master_id and domain_id belongs our bus side-band signal info. It can
> > > > help us to find the violation master.
> > >
> > > Does 'violation master' means the hardware could access the protected
> > > register? (ex. CPU, GCE, ...) If so, I think it's better to add
> > > comment to explain how to map (master_id, domain_id) to a hardware
> > > (maybe the device in device tree) because every body does not know
> > > what the number means. Don't try to translate the number to a string
> > > because this would cost much time to do this. Just print a number and
> > > we could find out the master by the comment.
> >
> > 'violation master' means the master which violates the permission
> > control. For example, if we set permission 'Secure R/W only' as CPU to
> > spi register. When violation is triggered, it means CPU access spi
> > register through normal world instead of secure world, which is not
> > allowed.
> >
> > 'master_id' cannot use the simple comm

Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-08-03 Thread Neal Liu
On Tue, 2020-08-04 at 00:04 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年8月3日 週一 下午12:01寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Sat, 2020-08-01 at 08:12 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > This patch is for "mediatek,mt6779-devapc", so I think commit title
> > > should show the SoC ID.
> >
> > Okay, I'll change title to 'soc:mediatek: add mt6779 devapc driver'.
> >
> > >
> > > Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> > > >
> > > > MediaTek bus fabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violation is logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by mtk-devapc driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > > > ---
> > >
> > > [snip]
> > >
> > > > +
> > > > +struct mtk_devapc_context {
> > > > +   struct device *dev;
> > > > +   u32 vio_idx_num;
> > > > +   void __iomem *devapc_pd_base;
> > > > +   struct mtk_devapc_vio_info *vio_info;
> > > > +   const struct mtk_devapc_pd_offset *offset;
> > > > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > > > +};
> > >
> > > I think this structure should separate the constant part. The constant 
> > > part is:
> > >
> > > struct mtk_devapc_data {
> > > const u32 vio_idx_num;
> > > const struct mtk_devapc_pd_offset *offset; /* I would like to
> > > remove struct mtk_devapc_pd_offset and directly put its member into
> > > this structure */
> > > const struct mtk_devapc_vio_dbgs *vio_dbgs; /* This may disappear */
> > > };
> > >
> > > And the context is:
> > >
> > > struct mtk_devapc_context {
> > > struct device *dev;
> > > void __iomem *devapc_pd_base;
> > > const struct mtk_devapc_data *data;
> > > };
> > >
> > > So when you define this, you would not waste memory to store non-constant 
> > > data.
> > >
> > > static const struct mtk_devapc_data devapc_mt6779 = {
> > >  .vio_idx_num = 510,
> > >  .offset = _pd_offset,
> > >  .vio_dbgs = _vio_dbgs,
> > > };
> > >
> >
> > Sorry, I still don't understand why this refactoring will not waste
> > memory to store non-constant data. Could you explain more details?
> > To my understanding, we still also have to allocate memory to store dev
> > & devapc_pd_base.
> 
> In some situation, it is. You make the non-constant data a global
> variable. I think the context data should be dynamic allocated. If
> this driver is not probed, the non-constant data occupy the memory.
> 

I got your point! In this case, we can save these 2 data structure
space, right?

struct device *dev;
void __iomem *devapc_pd_base;

I'll refactoring this data structures on next patch. Thanks !

> Regards,
> Chun-Kuang.
> 
> >
> > > Regards,
> > > Chun-Kuang.
> > >
> > > > +
> > > > +#endif /* __MTK_DEVAPC_H__ */
> > > > --
> > > > 1.7.9.5
> > > > ___
> > > > Linux-mediatek mailing list
> > > > linux-media...@lists.infradead.org
> > > > http://lists.infradead.org/mailman/listinfo/linux-mediatek
> >



Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-08-02 Thread Neal Liu
Hi Chun-Kuang,

On Sun, 2020-08-02 at 07:50 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +struct mtk_devapc_context {
> > +   struct device *dev;
> > +   u32 vio_idx_num;
> > +   void __iomem *devapc_pd_base;
> 
> This is devapc context, so prefix 'devapc' is redundant.
> And, what does 'pd' mean?

'pd' means power down. Of course we would also remove it as well.
I suggest to change it as 'infra_base'.

> 
> Regards,
> Chun-Kuang.
> 
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   const struct mtk_devapc_pd_offset *offset;
> > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > +};
> > +



Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-08-02 Thread Neal Liu
Hi Chun-Kuang,

On Sat, 2020-08-01 at 08:12 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> This patch is for "mediatek,mt6779-devapc", so I think commit title
> should show the SoC ID.

Okay, I'll change title to 'soc:mediatek: add mt6779 devapc driver'.

> 
> Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +struct mtk_devapc_context {
> > +   struct device *dev;
> > +   u32 vio_idx_num;
> > +   void __iomem *devapc_pd_base;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   const struct mtk_devapc_pd_offset *offset;
> > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > +};
> 
> I think this structure should separate the constant part. The constant part 
> is:
> 
> struct mtk_devapc_data {
> const u32 vio_idx_num;
> const struct mtk_devapc_pd_offset *offset; /* I would like to
> remove struct mtk_devapc_pd_offset and directly put its member into
> this structure */
> const struct mtk_devapc_vio_dbgs *vio_dbgs; /* This may disappear */
> };
> 
> And the context is:
> 
> struct mtk_devapc_context {
> struct device *dev;
> void __iomem *devapc_pd_base;
> const struct mtk_devapc_data *data;
> };
> 
> So when you define this, you would not waste memory to store non-constant 
> data.
> 
> static const struct mtk_devapc_data devapc_mt6779 = {
>  .vio_idx_num = 510,
>  .offset = _pd_offset,
>  .vio_dbgs = _vio_dbgs,
> };
> 

Sorry, I still don't understand why this refactoring will not waste
memory to store non-constant data. Could you explain more details?
To my understanding, we still also have to allocate memory to store dev
& devapc_pd_base.

> Regards,
> Chun-Kuang.
> 
> > +
> > +#endif /* __MTK_DEVAPC_H__ */
> > --
> > 1.7.9.5
> > ___
> > Linux-mediatek mailing list
> > linux-media...@lists.infradead.org
> > http://lists.infradead.org/mailman/listinfo/linux-mediatek



Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-08-02 Thread Neal Liu
Hi Chun-Kuang,

On Fri, 2020-07-31 at 23:55 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月31日 週五 上午10:52寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Fri, 2020-07-31 at 00:14 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> > > >
> > > > MediaTek bus fabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violation is logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by mtk-devapc driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > > > ---
> > >
> > > [snip]
> > >
> > > > +
> > > > +/*
> > > > + * devapc_extract_vio_dbg - extract full violation information after 
> > > > doing
> > > > + *  shift mechanism.
> > > > + */
> > > > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > > > +{
> > > > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > > > +   struct mtk_devapc_vio_info *vio_info;
> > > > +   void __iomem *vio_dbg0_reg;
> > > > +   void __iomem *vio_dbg1_reg;
> > > > +   u32 dbg0;
> > > > +
> > > > +   vio_dbg0_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg0;
> > > > +   vio_dbg1_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg1;
> > > > +
> > > > +   vio_dbgs = ctx->vio_dbgs;
> > > > +   vio_info = ctx->vio_info;
> > > > +
> > > > +   /* Starts to extract violation information */
> > > > +   dbg0 = readl(vio_dbg0_reg);
> > > > +   vio_info->vio_addr = readl(vio_dbg1_reg);
> > > > +
> > > > +   vio_info->master_id = (dbg0 & vio_dbgs->mstid.mask) >>
> > > > + vio_dbgs->mstid.start;
> > > > +   vio_info->domain_id = (dbg0 & vio_dbgs->dmnid.mask) >>
> > > > + vio_dbgs->dmnid.start;
> > > > +   vio_info->write = ((dbg0 & vio_dbgs->vio_w.mask) >>
> > > > +   vio_dbgs->vio_w.start) == 1;
> > > > +   vio_info->read = ((dbg0 & vio_dbgs->vio_r.mask) >>
> > > > + vio_dbgs->vio_r.start) == 1;
> > > > +   vio_info->vio_addr_high = (dbg0 & vio_dbgs->addr_h.mask) >>
> > > > + vio_dbgs->addr_h.start;
> > >
> > >
> > > I would like to define the type of ctx->vio_info to be
> > >
> > > struct mtk_devapc_vio_dbgs {
> > > u32 mstid:16;
> > > u32 dmnid:6;
> > > u32 vio_w:1;
> > > u32 vio_r:1;
> > > u32 addr_h:4;
> > > u32 resv:4;
> > > };
> > >
> > > so the code would like the simple way
> > >
> > > ctx->vio_info = (struct mtk_devapc_vio_dbgs)readl(vio_dbg1_reg);
> > >
> >
> > This idea looks great! Is there any possible to pass the bit layout by
> > DT data, and still make this operation simple?
> > Why am I asking this question is because this bit layout is platform
> > dependent.
> 
> I doubt these info would be in a single 32-bits register for all
> future SoC. If they are not in single 32-bits register, you may create
> a vio_dbgs_type in DT data, and the code may be
> 
> if (ctx->vio_dbgs_type == VIO_DBGS_TYPE_MT) {
> ctx->vio_info = (struct mtk_devapc_vio_dbgs)readl(vio_dbg1_reg);
> } else if (ctx->vio_dbgs_type == VIO_DBGS_TYPE_MT) {
> ctx->vio_info->mstid = readl(vio_mstid_reg);
> ctx->vio_info->dmnid = readl(vio_dmnid_reg);
> ctx->vio_info->vio_w = readl(vio_vio_w_reg);
> ctx->vio_info->vio_r = readl(vio_vio_r_reg);
> }
> 
> I think we need not to consider how the future would be. Once the
> second SoC driver is upstreaming, we could find out the best solution
> for it.
> 

Okay, I'll apply this on next patch.
Thanks !

> Regards,
> Chun-Kuang.
> 
> >
> > > Regards,
> > > Chun-Kuang.
> > >
> > > > +
> > > > +   devapc_vio_info_print(ctx);
> > > > +}
> > > > +
> >



Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-08-02 Thread Neal Liu
Hi Chun-Kuang,

On Fri, 2020-07-31 at 23:03 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月31日 週五 上午10:44寫道:
> >
> > Hi Chun-Kuang,
> >
> >
> > On Thu, 2020-07-30 at 00:38 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> > > >
> > > > MediaTek bus fabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violation is logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by mtk-devapc driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > > > ---
> > >
> > > [snip]
> > >
> > > > +
> > > > +static int get_shift_group(struct mtk_devapc_context *ctx)
> > > > +{
> > > > +   u32 vio_shift_sta;
> > > > +   void __iomem *reg;
> > > > +
> > > > +   reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sta;
> > > > +   vio_shift_sta = readl(reg);
> > > > +
> > > > +   if (vio_shift_sta)
> > > > +   return __ffs(vio_shift_sta);
> > > > +
> > > > +   return -EIO;
> > > > +}
> > >
> > > get_shift_group() is a small function, I would like to merge this
> > > function into sync_vio_dbg() to make code more simple.
> >
> > This function have a specific functionality. And it would make this
> > driver more readability. I would like to keep it as a function. Is that
> > okay for you?
> 
> After merge, the function would be:
> 
> static bool sync_min_shift_group_vio_dbg(struct mtk_devapc_context *ctx)
> {
>  int min_shift_group;
>  int ret;
>  u32 val;
> 
>  /* find the minimum shift group which has violation */
>  val = readl(ctx->devapc_pd_base + ctx->offset->vio_shift_sta);
>  if (!val)
> return false;
> 
>  min_shift_group = __ffs(val);
> 
>  /* Assign the group to sync */
>  writel(0x1 << min_shift_group, ctx->devapc_pd_base +
> ctx->offset->vio_shift_sel);
> 
>  /* Start syncing */
>  writel(0x1, ctx->devapc_pd_base + ctx->offset->vio_shift_con);
> 
>  ret = readl_poll_timeout(pd_vio_shift_con_reg, val, val == 0x3, 0,
>  PHY_DEVAPC_TIMEOUT);
>  if (ret) {
>   dev_err(ctx->dev, "%s: Shift violation info failed\n", __func__);
>   return false;
>  }
> 
>  /* Stop syncing */
>  writel(0x0, ctx->devapc_pd_base + ctx->offset->vio_shift_con);
> 
>  /* ? */
>  writel(0x1 << min_shift_group, ctx->devapc_pd_base +
> ctx->offset->vio_shift_sta);
> 
>  return true;
> }
> 
> The whole function is to sync min_shift_group violation info, I don't
> know why separate any part to an independent function? Any function
> call would cause penalty on CPU performance, so I does not like to
> break this function. After good comment, I think every body could
> understand the function of each register.
> After the merge, the code would be so simple as:
> 
> while(sync_min_shift_group_vio_dbg(ctx))
> devapc_extract_vio_dbg(ctx);
> 

Okay, this looks good to me. I'll apply this on next patch.
Thanks !

> >
> > >
> > > > +
> > >
> > > [snip]
> > >
> > > > +
> > > > +#define PHY_DEVAPC_TIMEOUT 0x1
> > > > +
> > > > +/*
> > > > + * sync_vio_dbg - do "shift" mechansim" to get full violation 
> > > > information.
> > > > + *shift mechanism is depends on devapc hardware design.
> > > > + *Mediatek devapc set multiple slaves as a group. When 
> > > > violation
> > > > + *is triggered, violation info is kept inside devapc 
> > > > hardware.
> > > > + *Driver should do shift mechansim to "shift" full 
> > > > violation
> > > > + *info to VIO_DBGs registers.
> > > > + *
> > > > + */
> > > > +static int sync_vio_dbg(struct mtk_devapc_context *ctx, u32 shift_bit)
> > > > +{
> > > > +   void __iomem *pd_vio_shift_sta_reg;
> > > > +   void __iomem *pd_

Re: [PATCH] acpi: fix 'return' with no value build warning

2020-08-02 Thread Neal Liu
On Fri, 2020-07-31 at 13:33 +0200, Rafael J. Wysocki wrote:
> On Fri, Jul 31, 2020 at 5:39 AM Neal Liu  wrote:
> >
> > Fixing CFI issue which introduced by commit efe9711214e6 is
> > incomplete.
> > Add return value to fix return-type build warning.
> >
> > Signed-off-by: Neal Liu 
> 
> Applied with edited subject and changelog, but ->
> 
> > ---
> >  drivers/acpi/processor_idle.c |4 ++--
> >  1 file changed, 2 insertions(+), 2 deletions(-)
> >
> > diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
> > index 6ffb6c9..6870020 100644
> > --- a/drivers/acpi/processor_idle.c
> > +++ b/drivers/acpi/processor_idle.c
> > @@ -664,11 +664,11 @@ static int acpi_idle_enter_s2idle(struct 
> > cpuidle_device *dev,
> > struct acpi_processor *pr = __this_cpu_read(processors);
> >
> > if (unlikely(!pr))
> > -   return;
> > +   return -EFAULT;
> 
> -> there is no point returning an error code here, so I've made it
> just return 0.

return 0 is not matched with the meaning of contexts, but it's fine for
this patch.
Thanks !

> 
> >
> > if (pr->flags.bm_check) {
> > acpi_idle_enter_bm(pr, cx, false);
> > -   return;
> > +   return 0;
> > } else {
> > ACPI_FLUSH_CPU_CACHE();
> > }
> > --



[PATCH] acpi: fix 'return' with no value build warning

2020-07-30 Thread Neal Liu
Fixing CFI issue which introduced by commit efe9711214e6 is
incomplete.
Add return value to fix return-type build warning.

Signed-off-by: Neal Liu 
---
 drivers/acpi/processor_idle.c |4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
index 6ffb6c9..6870020 100644
--- a/drivers/acpi/processor_idle.c
+++ b/drivers/acpi/processor_idle.c
@@ -664,11 +664,11 @@ static int acpi_idle_enter_s2idle(struct cpuidle_device 
*dev,
struct acpi_processor *pr = __this_cpu_read(processors);
 
if (unlikely(!pr))
-   return;
+   return -EFAULT;
 
if (pr->flags.bm_check) {
acpi_idle_enter_bm(pr, cx, false);
-   return;
+   return 0;
} else {
ACPI_FLUSH_CPU_CACHE();
}
-- 
1.7.9.5


acpi: fix 'return' with no value build warning

2020-07-30 Thread Neal Liu
*** BLURB HERE ***

Neal Liu (1):
  acpi: fix 'return' with no value build warning

 drivers/acpi/processor_idle.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

-- 
2.18.0


Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-07-30 Thread Neal Liu
Hi Chun-Kuang,

On Fri, 2020-07-31 at 00:14 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +/*
> > + * devapc_extract_vio_dbg - extract full violation information after doing
> > + *  shift mechanism.
> > + */
> > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > +{
> > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   void __iomem *vio_dbg0_reg;
> > +   void __iomem *vio_dbg1_reg;
> > +   u32 dbg0;
> > +
> > +   vio_dbg0_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg0;
> > +   vio_dbg1_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg1;
> > +
> > +   vio_dbgs = ctx->vio_dbgs;
> > +   vio_info = ctx->vio_info;
> > +
> > +   /* Starts to extract violation information */
> > +   dbg0 = readl(vio_dbg0_reg);
> > +   vio_info->vio_addr = readl(vio_dbg1_reg);
> > +
> > +   vio_info->master_id = (dbg0 & vio_dbgs->mstid.mask) >>
> > + vio_dbgs->mstid.start;
> > +   vio_info->domain_id = (dbg0 & vio_dbgs->dmnid.mask) >>
> > + vio_dbgs->dmnid.start;
> > +   vio_info->write = ((dbg0 & vio_dbgs->vio_w.mask) >>
> > +   vio_dbgs->vio_w.start) == 1;
> > +   vio_info->read = ((dbg0 & vio_dbgs->vio_r.mask) >>
> > + vio_dbgs->vio_r.start) == 1;
> > +   vio_info->vio_addr_high = (dbg0 & vio_dbgs->addr_h.mask) >>
> > + vio_dbgs->addr_h.start;
> 
> 
> I would like to define the type of ctx->vio_info to be
> 
> struct mtk_devapc_vio_dbgs {
> u32 mstid:16;
> u32 dmnid:6;
> u32 vio_w:1;
> u32 vio_r:1;
> u32 addr_h:4;
> u32 resv:4;
> };
> 
> so the code would like the simple way
> 
> ctx->vio_info = (struct mtk_devapc_vio_dbgs)readl(vio_dbg1_reg);
> 

This idea looks great! Is there any possible to pass the bit layout by
DT data, and still make this operation simple?
Why am I asking this question is because this bit layout is platform
dependent.

> Regards,
> Chun-Kuang.
> 
> > +
> > +   devapc_vio_info_print(ctx);
> > +}
> > +



Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-07-30 Thread Neal Liu
Hi Chun-Kuang,


On Thu, 2020-07-30 at 06:47 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> 
> [snip]
> 
> > +
> > +static void devapc_vio_info_print(struct mtk_devapc_context *ctx)
> > +{
> > +   struct mtk_devapc_vio_info *vio_info = ctx->vio_info;
> > +
> > +   /* Print violation information */
> > +   if (vio_info->write)
> > +   dev_info(ctx->dev, "Write Violation\n");
> > +   else if (vio_info->read)
> > +   dev_info(ctx->dev, "Read Violation\n");
> > +
> > +   dev_info(ctx->dev, "Vio Addr:0x%x, High:0x%x, Bus ID:0x%x, Dom 
> > ID:%x\n",
> > +vio_info->vio_addr, vio_info->vio_addr_high,
> > +vio_info->master_id, vio_info->domain_id);
> > +}
> 
> devapc_vio_info_print() is small function and only called by
> devapc_extract_vio_dbg(), so I would like to merge this function into
> devapc_extract_vio_dbg() and you could drop struct mtk_devapc_vio_info
> because its member are all local variable.

This idea is okay for me. I'll update on next patch.
Thanks !

> 
> > +
> > +/*
> > + * devapc_extract_vio_dbg - extract full violation information after doing
> > + *  shift mechanism.
> > + */
> > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > +{
> > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   void __iomem *vio_dbg0_reg;
> > +   void __iomem *vio_dbg1_reg;
> > +   u32 dbg0;
> > +
> > +   vio_dbg0_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg0;
> > +   vio_dbg1_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg1;
> > +
> > +   vio_dbgs = ctx->vio_dbgs;
> > +   vio_info = ctx->vio_info;
> > +
> > +   /* Starts to extract violation information */
> > +   dbg0 = readl(vio_dbg0_reg);
> > +   vio_info->vio_addr = readl(vio_dbg1_reg);
> > +
> > +   vio_info->master_id = (dbg0 & vio_dbgs->mstid.mask) >>
> > + vio_dbgs->mstid.start;
> > +   vio_info->domain_id = (dbg0 & vio_dbgs->dmnid.mask) >>
> > + vio_dbgs->dmnid.start;
> > +   vio_info->write = ((dbg0 & vio_dbgs->vio_w.mask) >>
> > +   vio_dbgs->vio_w.start) == 1;
> > +   vio_info->read = ((dbg0 & vio_dbgs->vio_r.mask) >>
> > + vio_dbgs->vio_r.start) == 1;
> > +   vio_info->vio_addr_high = (dbg0 & vio_dbgs->addr_h.mask) >>
> > + vio_dbgs->addr_h.start;
> > +
> > +   devapc_vio_info_print(ctx);
> > +}
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * start_devapc - unmask slave's irq to start receiving devapc violation.
> > + */
> > +static void start_devapc(struct mtk_devapc_context *ctx)
> > +{
> > +   u32 vio_idx;
> > +
> > +   for (vio_idx = 0; vio_idx < ctx->vio_idx_num; vio_idx++)
> > +   mask_module_irq(ctx, vio_idx, false);
> 
> Are these bits default true? If they are default false, you need not
> to setup it to false again.

It's default value is true, which is mask.
We try to unmask it to start service.

> 
> > +}
> > +
> 
> [snip]
> 
> > diff --git a/drivers/soc/mediatek/mtk-devapc.h 
> > b/drivers/soc/mediatek/mtk-devapc.h
> > new file mode 100644
> > index 000..7bd7e66
> > --- /dev/null
> > +++ b/drivers/soc/mediatek/mtk-devapc.h
> > @@ -0,0 +1,54 @@
> > +/* SPDX-License-Identifier: GPL-2.0 */
> > +/*
> > + * Copyright (C) 2020 MediaTek Inc.
> > + */
> > +
> > +#ifndef __MTK_DEVAPC_H__
> > +#define __MTK_DEVAPC_H__
> > +
> > +#define VIO_MOD_TO_REG_IND(m)  ((m) / 32)
> > +#define VIO_MOD_TO_REG_OFF(m)  ((m) % 32)
> > +
> > +

Re: [PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-07-30 Thread Neal Liu
Hi Chun-Kuang,


On Thu, 2020-07-30 at 00:38 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月29日 週三 下午4:29寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +static int get_shift_group(struct mtk_devapc_context *ctx)
> > +{
> > +   u32 vio_shift_sta;
> > +   void __iomem *reg;
> > +
> > +   reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sta;
> > +   vio_shift_sta = readl(reg);
> > +
> > +   if (vio_shift_sta)
> > +   return __ffs(vio_shift_sta);
> > +
> > +   return -EIO;
> > +}
> 
> get_shift_group() is a small function, I would like to merge this
> function into sync_vio_dbg() to make code more simple.

This function have a specific functionality. And it would make this
driver more readability. I would like to keep it as a function. Is that
okay for you?

> 
> > +
> 
> [snip]
> 
> > +
> > +#define PHY_DEVAPC_TIMEOUT 0x1
> > +
> > +/*
> > + * sync_vio_dbg - do "shift" mechansim" to get full violation information.
> > + *shift mechanism is depends on devapc hardware design.
> > + *Mediatek devapc set multiple slaves as a group. When 
> > violation
> > + *is triggered, violation info is kept inside devapc 
> > hardware.
> > + *Driver should do shift mechansim to "shift" full 
> > violation
> > + *info to VIO_DBGs registers.
> > + *
> > + */
> > +static int sync_vio_dbg(struct mtk_devapc_context *ctx, u32 shift_bit)
> > +{
> > +   void __iomem *pd_vio_shift_sta_reg;
> > +   void __iomem *pd_vio_shift_sel_reg;
> > +   void __iomem *pd_vio_shift_con_reg;
> > +   int ret;
> > +   u32 val;
> > +
> > +   pd_vio_shift_sta_reg = ctx->devapc_pd_base + 
> > ctx->offset->vio_shift_sta;
> > +   pd_vio_shift_sel_reg = ctx->devapc_pd_base + 
> > ctx->offset->vio_shift_sel;
> > +   pd_vio_shift_con_reg = ctx->devapc_pd_base + 
> > ctx->offset->vio_shift_con;
> > +
> > +   /* Enable shift mechansim */
> > +   writel(0x1 << shift_bit, pd_vio_shift_sel_reg);
> > +   writel(0x1, pd_vio_shift_con_reg);
> > +
> > +   ret = readl_poll_timeout(pd_vio_shift_con_reg, val, val == 0x3, 0,
> > +PHY_DEVAPC_TIMEOUT);
> > +   if (ret)
> > +   dev_err(ctx->dev, "%s: Shift violation info failed\n", 
> > __func__);
> > +
> > +   /* Disable shift mechanism */
> > +   writel(0x0, pd_vio_shift_con_reg);
> > +   writel(0x0, pd_vio_shift_sel_reg);
> > +   writel(0x1 << shift_bit, pd_vio_shift_sta_reg);
> > +
> > +   return ret;
> > +}
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * devapc_extract_vio_dbg - extract full violation information after doing
> > + *  shift mechanism.
> > + */
> > +static void devapc_extract_vio_dbg(struct mtk_devapc_context *ctx)
> > +{
> > +   const struct mtk_devapc_vio_dbgs *vio_dbgs;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   void __iomem *vio_dbg0_reg;
> > +   void __iomem *vio_dbg1_reg;
> > +   u32 dbg0;
> > +
> > +   vio_dbg0_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg0;
> > +   vio_dbg1_reg = ctx->devapc_pd_base + ctx->offset->vio_dbg1;
> > +
> > +   vio_dbgs = ctx->vio_dbgs;
> > +   vio_info = ctx->vio_info;
> > +
> > +   /* Starts to extract violation information */
> > +   dbg0 = readl(vio_dbg0_reg);
> > +   vio_info->vio_addr = readl(vio_dbg1_reg);
> > +
> > +   vio_info->master_id = (dbg0 & vio_dbgs->mstid.mask) >>
> > + vio_dbgs->mstid.start;
> 
> What is master_id? How could we use it to debug? For example, if we
> get a master_id = 1, what should we do for this?
> 
> > +   

Re: linux-next: build warning after merge of the pm tree

2020-07-29 Thread Neal Liu
This warning should be fixed also.
Should I send another patch?

Thanks !

On Thu, 2020-07-30 at 12:55 +1000, Stephen Rothwell wrote:
> Hi all,
> 
> After merging the pm tree, today's linux-next build (x86_64 allmodconfig)
> produced this warning:
> 
> drivers/acpi/processor_idle.c: In function 'acpi_idle_enter_s2idle':
> drivers/acpi/processor_idle.c:666:4: warning: 'return' with no value, in 
> function returning non-void [-Wreturn-type]
>   666 |return;
>   |^~
> drivers/acpi/processor_idle.c:657:12: note: declared here
>   657 | static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
>   |^~
> drivers/acpi/processor_idle.c:670:4: warning: 'return' with no value, in 
> function returning non-void [-Wreturn-type]
>   670 |return;
>   |^~
> drivers/acpi/processor_idle.c:657:12: note: declared here
>   657 | static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
>   |^~
> 
> Introduced by commit
> 
>   efe9711214e6 ("cpuidle: change enter_s2idle() prototype")
> 



[PATCH v4 2/2] soc: mediatek: add mtk-devapc driver

2020-07-29 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 ++
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  323 +
 drivers/soc/mediatek/mtk-devapc.h |   54 +++
 4 files changed, 387 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c
 create mode 100644 drivers/soc/mediatek/mtk-devapc.h

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..db751d0
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,323 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include "mtk-devapc.h"
+
+static int get_shift_group(struct mtk_devapc_context *ctx)
+{
+   u32 vio_shift_sta;
+   void __iomem *reg;
+
+   reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sta;
+   vio_shift_sta = readl(reg);
+
+   if (vio_shift_sta)
+   return __ffs(vio_shift_sta);
+
+   return -EIO;
+}
+
+static void clear_vio_status(struct mtk_devapc_context *ctx, u32 module)
+{
+   void __iomem *reg;
+
+   reg = ctx->devapc_pd_base + ctx->offset->vio_sta;
+   reg += 0x4 * VIO_MOD_TO_REG_IND(module);
+
+   writel(0x1 << VIO_MOD_TO_REG_OFF(module), reg);
+}
+
+static void mask_module_irq(struct mtk_devapc_context *ctx, u32 module,
+   bool mask)
+{
+   void __iomem *reg;
+   u32 value;
+
+   reg = ctx->devapc_pd_base + ctx->offset->vio_mask;
+   reg += 0x4 * VIO_MOD_TO_REG_IND(module);
+
+   value = readl(reg);
+   if (mask)
+   value |= (0x1 << VIO_MOD_TO_REG_OFF(module));
+   else
+   value &= ~(0x1 << VIO_MOD_TO_REG_OFF(module));
+
+   writel(value, reg);
+}
+
+#define PHY_DEVAPC_TIMEOUT 0x1
+
+/*
+ * sync_vio_dbg - do "shift" mechansim" to get full violation information.
+ *shift mechanism is depends on devapc hardware design.
+ *Mediatek devapc set multiple slaves as a group. When 
violation
+ *is triggered, violation info is kept inside devapc hardware.
+ *Driver should do shift mechansim to "shift" full violation
+ *info to VIO_DBGs registers.
+ *
+ */
+static int sync_vio_dbg(struct mtk_devapc_context *ctx, u32 shift_bit)
+{
+   void __iomem *pd_vio_shift_sta_reg;
+   void __iomem *pd_vio_shift_sel_reg;
+   void __iomem *pd_vio_shift_con_reg;
+   int ret;
+   u32 val;
+
+   pd_vio_shift_sta_reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sta;
+   pd_vio_shift_sel_reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sel;
+   pd_vio_shift_con_reg = ctx->devapc_pd_base + ctx->offset->vio_shift_con;
+
+   /* Enable shift mechansim */
+   writel(0x1 << shift_bit, pd_vio_shift_sel_reg);
+   writel(0x1, pd_vio_shift_con_reg);
+
+   ret = readl_poll_timeout(pd_vio_shift_con_reg, val, val == 0x3, 0,
+PHY_DEVAPC_TIMEOUT);
+   if (ret)
+   dev_err(ctx->dev, "%s: Shift violation info failed\n", 
__fun

[PATCH v4 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-07-29 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..6c763f8
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


[PATCH v4] Add MediaTek MT6779 devapc driver

2020-07-29 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further analysis 
or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v3:
- revise violation handling flow to make it more easily to understand
  hardware behavior.
- add more comments to understand how hardware works.

changes since v2:
- pass platform info through DT data.
- remove unnecessary function.
- remove slave_type because it always equals to 1 in current support SoC.
- use vio_idx_num instread of list all devices' index.
- add more comments to describe hardware behavior.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mtk-devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  58 
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 323 ++
 drivers/soc/mediatek/mtk-devapc.h |  54 +++
 5 files changed, 445 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c
 create mode 100644 drivers/soc/mediatek/mtk-devapc.h

-- 
2.18.0


Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-28 Thread Neal Liu
On Wed, 2020-07-29 at 10:22 +0800, Chun-Kuang Hu wrote:
> Neal Liu  於 2020年7月29日 週三 上午10:10寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Tue, 2020-07-28 at 23:35 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月28日 週二 上午11:52寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > On Mon, 2020-07-27 at 22:47 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月27日 週一 上午11:06寫道:
> > > > > >
> > > > > > Hi Chun-Kuang,
> > > > > >
> > > > > > On Fri, 2020-07-24 at 23:55 +0800, Chun-Kuang Hu wrote:
> > > > > > > Hi, Neal:
> > > > > > >
> > > > > > > Neal Liu  於 2020年7月24日 週五 下午2:55寫道:
> > > > > > > >
> > > > > > > > Hi Chun-Kuang,
> > > > > > > >
> > > > > > > > On Fri, 2020-07-24 at 00:32 +0800, Chun-Kuang Hu wrote:
> > > > > > > > > Hi, Neal:
> > > > > > > > >
> > > > > > > > > Neal Liu  於 2020年7月23日 週四 下午2:11寫道:
> > > > > > > > > >
> > > > > > > > > > Hi Chun-Kuang,
> > > > > > > > > >
> > > > > > > > > > On Wed, 2020-07-22 at 22:25 +0800, Chun-Kuang Hu wrote:
> > > > > > > > > > > Hi, Neal:
> > > > > > > > > > >
> > > > > > > > > > > Neal Liu  於 2020年7月22日 週三 
> > > > > > > > > > > 上午11:49寫道:
> > > > > > > > > > > >
> > > > > > > > > > > > Hi Chun-Kuang,
> > > > > > > > > > > >
> > > > > > > > > > > > On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> > > > > > > > > > > > > Hi, Neal:
> > > > > > > > > > > > >
> > > > > > > > > > > > > Neal Liu  於 2020年7月21日 週二 
> > > > > > > > > > > > > 下午12:00寫道:
> > > > > > > > > > > > > >
> > > > > > > > > > > > >
> > > > > > > > > > > > > > +
> > > > > > > > > > > > > > +/*
> > > > > > > > > > > > > > + * mtk_devapc_dump_vio_dbg - get the violation 
> > > > > > > > > > > > > > index and dump the full violation
> > > > > > > > > > > > > > + *   debug information.
> > > > > > > > > > > > > > + */
> > > > > > > > > > > > > > +static bool mtk_devapc_dump_vio_dbg(struct 
> > > > > > > > > > > > > > mtk_devapc_context *ctx, u32 vio_idx)
> > > > > > > > > > > > > > +{
> > > > > > > > > > > > > > +   u32 shift_bit;
> > > > > > > > > > > > > > +
> > > > > > > > > > > > > > +   if (check_vio_mask(ctx, vio_idx))
> > > > > > > > > > > > > > +   return false;
> > > > > > > > > > > > > > +
> > > > > > > > > > > > > > +   if (!check_vio_status(ctx, vio_idx))
> > > > > > > > > > > > > > +   return false;
> > > > > > > > > > > > > > +
> > > > > > > > > > > > > > +   shift_bit = get_shift_group(ctx, vio_idx);
> > > > > > > > > > > > > > +
> > > > > > > > > > > > > > +   if (sync_vio_dbg(ctx, shift_bit))
> > > > > > > > > > > > > > +   return false;
> > > > > > > > > > > > > > +
> > > > > > > > > > > > > > +   devapc_extract_vio_dbg(ctx);
> > > > > > > > > > > > >
> > > > > > > > > > > > > I think get_shift_group(), syn

Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-28 Thread Neal Liu
Hi Chun-Kuang,

On Tue, 2020-07-28 at 23:35 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月28日 週二 上午11:52寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Mon, 2020-07-27 at 22:47 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月27日 週一 上午11:06寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > On Fri, 2020-07-24 at 23:55 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月24日 週五 下午2:55寫道:
> > > > > >
> > > > > > Hi Chun-Kuang,
> > > > > >
> > > > > > On Fri, 2020-07-24 at 00:32 +0800, Chun-Kuang Hu wrote:
> > > > > > > Hi, Neal:
> > > > > > >
> > > > > > > Neal Liu  於 2020年7月23日 週四 下午2:11寫道:
> > > > > > > >
> > > > > > > > Hi Chun-Kuang,
> > > > > > > >
> > > > > > > > On Wed, 2020-07-22 at 22:25 +0800, Chun-Kuang Hu wrote:
> > > > > > > > > Hi, Neal:
> > > > > > > > >
> > > > > > > > > Neal Liu  於 2020年7月22日 週三 上午11:49寫道:
> > > > > > > > > >
> > > > > > > > > > Hi Chun-Kuang,
> > > > > > > > > >
> > > > > > > > > > On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> > > > > > > > > > > Hi, Neal:
> > > > > > > > > > >
> > > > > > > > > > > Neal Liu  於 2020年7月21日 週二 
> > > > > > > > > > > 下午12:00寫道:
> > > > > > > > > > > >
> > > > > > > > > > >
> > > > > > > > > > > > +
> > > > > > > > > > > > +/*
> > > > > > > > > > > > + * mtk_devapc_dump_vio_dbg - get the violation index 
> > > > > > > > > > > > and dump the full violation
> > > > > > > > > > > > + *   debug information.
> > > > > > > > > > > > + */
> > > > > > > > > > > > +static bool mtk_devapc_dump_vio_dbg(struct 
> > > > > > > > > > > > mtk_devapc_context *ctx, u32 vio_idx)
> > > > > > > > > > > > +{
> > > > > > > > > > > > +   u32 shift_bit;
> > > > > > > > > > > > +
> > > > > > > > > > > > +   if (check_vio_mask(ctx, vio_idx))
> > > > > > > > > > > > +   return false;
> > > > > > > > > > > > +
> > > > > > > > > > > > +   if (!check_vio_status(ctx, vio_idx))
> > > > > > > > > > > > +   return false;
> > > > > > > > > > > > +
> > > > > > > > > > > > +   shift_bit = get_shift_group(ctx, vio_idx);
> > > > > > > > > > > > +
> > > > > > > > > > > > +   if (sync_vio_dbg(ctx, shift_bit))
> > > > > > > > > > > > +   return false;
> > > > > > > > > > > > +
> > > > > > > > > > > > +   devapc_extract_vio_dbg(ctx);
> > > > > > > > > > >
> > > > > > > > > > > I think get_shift_group(), sync_vio_dbg(), and
> > > > > > > > > > > devapc_extract_vio_dbg() should be moved out of vio_idx 
> > > > > > > > > > > for-loop (the
> > > > > > > > > > > loop in devapc_violation_irq()) because these three 
> > > > > > > > > > > function is not
> > > > > > > > > > > related to vio_idx.
> > > > > > > > > > > Another question: when multiple vio_idx violation occur, 
> > > > > > > > > > > vio_addr is
> > > > > > > > > > > related to which one vio_idx? The latest happened one?
> > > > > > > > > > >
> > > > > > > > > >
> > > > > > > > 

Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-27 Thread Neal Liu
Hi Chun-Kuang,

On Mon, 2020-07-27 at 22:47 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月27日 週一 上午11:06寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Fri, 2020-07-24 at 23:55 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月24日 週五 下午2:55寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > On Fri, 2020-07-24 at 00:32 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月23日 週四 下午2:11寫道:
> > > > > >
> > > > > > Hi Chun-Kuang,
> > > > > >
> > > > > > On Wed, 2020-07-22 at 22:25 +0800, Chun-Kuang Hu wrote:
> > > > > > > Hi, Neal:
> > > > > > >
> > > > > > > Neal Liu  於 2020年7月22日 週三 上午11:49寫道:
> > > > > > > >
> > > > > > > > Hi Chun-Kuang,
> > > > > > > >
> > > > > > > > On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> > > > > > > > > Hi, Neal:
> > > > > > > > >
> > > > > > > > > Neal Liu  於 2020年7月21日 週二 下午12:00寫道:
> > > > > > > > > >
> > > > > > > > >
> > > > > > > > > > +
> > > > > > > > > > +/*
> > > > > > > > > > + * mtk_devapc_dump_vio_dbg - get the violation index and 
> > > > > > > > > > dump the full violation
> > > > > > > > > > + *   debug information.
> > > > > > > > > > + */
> > > > > > > > > > +static bool mtk_devapc_dump_vio_dbg(struct 
> > > > > > > > > > mtk_devapc_context *ctx, u32 vio_idx)
> > > > > > > > > > +{
> > > > > > > > > > +   u32 shift_bit;
> > > > > > > > > > +
> > > > > > > > > > +   if (check_vio_mask(ctx, vio_idx))
> > > > > > > > > > +   return false;
> > > > > > > > > > +
> > > > > > > > > > +   if (!check_vio_status(ctx, vio_idx))
> > > > > > > > > > +   return false;
> > > > > > > > > > +
> > > > > > > > > > +   shift_bit = get_shift_group(ctx, vio_idx);
> > > > > > > > > > +
> > > > > > > > > > +   if (sync_vio_dbg(ctx, shift_bit))
> > > > > > > > > > +   return false;
> > > > > > > > > > +
> > > > > > > > > > +   devapc_extract_vio_dbg(ctx);
> > > > > > > > >
> > > > > > > > > I think get_shift_group(), sync_vio_dbg(), and
> > > > > > > > > devapc_extract_vio_dbg() should be moved out of vio_idx 
> > > > > > > > > for-loop (the
> > > > > > > > > loop in devapc_violation_irq()) because these three function 
> > > > > > > > > is not
> > > > > > > > > related to vio_idx.
> > > > > > > > > Another question: when multiple vio_idx violation occur, 
> > > > > > > > > vio_addr is
> > > > > > > > > related to which one vio_idx? The latest happened one?
> > > > > > > > >
> > > > > > > >
> > > > > > > > Actually, it's related to vio_idx. But we don't use it directly 
> > > > > > > > on these
> > > > > > > > function. I think below snip code might be better way to 
> > > > > > > > understand it.
> > > > > > > >
> > > > > > > > for (...)
> > > > > > > > {
> > > > > > > > check_vio_mask()
> > > > > > > > check_vio_status()
> > > > > > > >
> > > > > > > > // if get vio_idx, mask it temporarily
> > > > > > > > mask_module_irq(true)
> > > > > > > > clear_vio_status()
> > > > > > > >
> > > > > > > > // dump violation info
>

[PATCH v3] cpuidle: Fix CFI failure

2020-07-26 Thread Neal Liu
changes since v2:
- add more comments on enter_s2idle to explain why it is necessary to return
  int even if its return value is never used.

changes since v1:
- add more description in commit message.

*** BLURB HERE ***

Neal Liu (1):
  cpuidle: change enter_s2idle() prototype

 drivers/acpi/processor_idle.c   | 6 --
 drivers/cpuidle/cpuidle-tegra.c | 8 +---
 drivers/idle/intel_idle.c   | 6 --
 include/linux/cpuidle.h | 9 ++---
 4 files changed, 19 insertions(+), 10 deletions(-)

-- 
2.18.0


[PATCH v3] cpuidle: change enter_s2idle() prototype

2020-07-26 Thread Neal Liu
Control Flow Integrity(CFI) is a security mechanism that disallows
changes to the original control flow graph of a compiled binary,
making it significantly harder to perform such attacks.

init_state_node() assign same function callback to different
function pointer declarations.

static int init_state_node(struct cpuidle_state *idle_state,
   const struct of_device_id *matches,
   struct device_node *state_node) { ...
idle_state->enter = match_id->data; ...
idle_state->enter_s2idle = match_id->data; }

Function declarations:

struct cpuidle_state { ...
int (*enter) (struct cpuidle_device *dev,
  struct cpuidle_driver *drv,
  int index);

void (*enter_s2idle) (struct cpuidle_device *dev,
  struct cpuidle_driver *drv,
  int index); };

In this case, either enter() or enter_s2idle() would cause CFI check
failed since they use same callee.

Align function prototype of enter() since it needs return value for
some use cases. The return value of enter_s2idle() is no
need currently.

Signed-off-by: Neal Liu 
Reviewed-by: Sami Tolvanen 
---
 drivers/acpi/processor_idle.c   |6 --
 drivers/cpuidle/cpuidle-tegra.c |8 +---
 drivers/idle/intel_idle.c   |6 --
 include/linux/cpuidle.h |9 ++---
 4 files changed, 19 insertions(+), 10 deletions(-)

diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
index 75534c5..6ffb6c9 100644
--- a/drivers/acpi/processor_idle.c
+++ b/drivers/acpi/processor_idle.c
@@ -655,8 +655,8 @@ static int acpi_idle_enter(struct cpuidle_device *dev,
return index;
 }
 
-static void acpi_idle_enter_s2idle(struct cpuidle_device *dev,
-  struct cpuidle_driver *drv, int index)
+static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
+ struct cpuidle_driver *drv, int index)
 {
struct acpi_processor_cx *cx = per_cpu(acpi_cstate[index], dev->cpu);
 
@@ -674,6 +674,8 @@ static void acpi_idle_enter_s2idle(struct cpuidle_device 
*dev,
}
}
acpi_idle_do_entry(cx);
+
+   return 0;
 }
 
 static int acpi_processor_setup_cpuidle_cx(struct acpi_processor *pr,
diff --git a/drivers/cpuidle/cpuidle-tegra.c b/drivers/cpuidle/cpuidle-tegra.c
index 1500458..a12fb14 100644
--- a/drivers/cpuidle/cpuidle-tegra.c
+++ b/drivers/cpuidle/cpuidle-tegra.c
@@ -253,11 +253,13 @@ static int tegra_cpuidle_enter(struct cpuidle_device *dev,
return err ? -1 : index;
 }
 
-static void tegra114_enter_s2idle(struct cpuidle_device *dev,
- struct cpuidle_driver *drv,
- int index)
+static int tegra114_enter_s2idle(struct cpuidle_device *dev,
+struct cpuidle_driver *drv,
+int index)
 {
tegra_cpuidle_enter(dev, drv, index);
+
+   return 0;
 }
 
 /*
diff --git a/drivers/idle/intel_idle.c b/drivers/idle/intel_idle.c
index f449584..b178da3 100644
--- a/drivers/idle/intel_idle.c
+++ b/drivers/idle/intel_idle.c
@@ -175,13 +175,15 @@ static __cpuidle int intel_idle(struct cpuidle_device 
*dev,
  * Invoked as a suspend-to-idle callback routine with frozen user space, frozen
  * scheduler tick and suspended scheduler clock on the target CPU.
  */
-static __cpuidle void intel_idle_s2idle(struct cpuidle_device *dev,
-   struct cpuidle_driver *drv, int index)
+static __cpuidle int intel_idle_s2idle(struct cpuidle_device *dev,
+  struct cpuidle_driver *drv, int index)
 {
unsigned long eax = flg2MWAIT(drv->states[index].flags);
unsigned long ecx = 1; /* break on interrupt flag */
 
mwait_idle_with_hints(eax, ecx);
+
+   return 0;
 }
 
 /*
diff --git a/include/linux/cpuidle.h b/include/linux/cpuidle.h
index ec2ef63..b65909a 100644
--- a/include/linux/cpuidle.h
+++ b/include/linux/cpuidle.h
@@ -65,10 +65,13 @@ struct cpuidle_state {
 * CPUs execute ->enter_s2idle with the local tick or entire timekeeping
 * suspended, so it must not re-enable interrupts at any point (even
 * temporarily) or attempt to change states of clock event devices.
+*
+* This callback may point to the same function as ->enter if all of
+* the above requirements are met by it.
 */
-   void (*enter_s2idle) (struct cpuidle_device *dev,
- struct cpuidle_driver *drv,
- int index);
+   int (*enter_s2idle)(struct cpuidle_device *dev,
+   struct cpuidle_driver *drv,
+   int index);
 };
 
 /* Idle State Flags */
-- 
1.7.9.5


Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-26 Thread Neal Liu
Hi Chun-Kuang,

On Fri, 2020-07-24 at 23:55 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月24日 週五 下午2:55寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Fri, 2020-07-24 at 00:32 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月23日 週四 下午2:11寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > On Wed, 2020-07-22 at 22:25 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月22日 週三 上午11:49寫道:
> > > > > >
> > > > > > Hi Chun-Kuang,
> > > > > >
> > > > > > On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> > > > > > > Hi, Neal:
> > > > > > >
> > > > > > > Neal Liu  於 2020年7月21日 週二 下午12:00寫道:
> > > > > > > >
> > > > > > >
> > > > > > > > +
> > > > > > > > +/*
> > > > > > > > + * mtk_devapc_dump_vio_dbg - get the violation index and dump 
> > > > > > > > the full violation
> > > > > > > > + *   debug information.
> > > > > > > > + */
> > > > > > > > +static bool mtk_devapc_dump_vio_dbg(struct mtk_devapc_context 
> > > > > > > > *ctx, u32 vio_idx)
> > > > > > > > +{
> > > > > > > > +   u32 shift_bit;
> > > > > > > > +
> > > > > > > > +   if (check_vio_mask(ctx, vio_idx))
> > > > > > > > +   return false;
> > > > > > > > +
> > > > > > > > +   if (!check_vio_status(ctx, vio_idx))
> > > > > > > > +   return false;
> > > > > > > > +
> > > > > > > > +   shift_bit = get_shift_group(ctx, vio_idx);
> > > > > > > > +
> > > > > > > > +   if (sync_vio_dbg(ctx, shift_bit))
> > > > > > > > +   return false;
> > > > > > > > +
> > > > > > > > +   devapc_extract_vio_dbg(ctx);
> > > > > > >
> > > > > > > I think get_shift_group(), sync_vio_dbg(), and
> > > > > > > devapc_extract_vio_dbg() should be moved out of vio_idx for-loop 
> > > > > > > (the
> > > > > > > loop in devapc_violation_irq()) because these three function is 
> > > > > > > not
> > > > > > > related to vio_idx.
> > > > > > > Another question: when multiple vio_idx violation occur, vio_addr 
> > > > > > > is
> > > > > > > related to which one vio_idx? The latest happened one?
> > > > > > >
> > > > > >
> > > > > > Actually, it's related to vio_idx. But we don't use it directly on 
> > > > > > these
> > > > > > function. I think below snip code might be better way to understand 
> > > > > > it.
> > > > > >
> > > > > > for (...)
> > > > > > {
> > > > > > check_vio_mask()
> > > > > > check_vio_status()
> > > > > >
> > > > > > // if get vio_idx, mask it temporarily
> > > > > > mask_module_irq(true)
> > > > > > clear_vio_status()
> > > > > >
> > > > > > // dump violation info
> > > > > > get_shift_group()
> > > > > > sync_vio_dbg()
> > > > > > devapc_extract_vio_dbg()
> > > > > >
> > > > > > // unmask
> > > > > > mask_module_irq(false)
> > > > > > }
> > > > >
> > > > > This snip code does not explain any thing. I could rewrite this code 
> > > > > as:
> > > > >
> > > > > for (...)
> > > > > {
> > > > > check_vio_mask()
> > > > > check_vio_status()
> > > > >
> > > > > // if get vio_idx, mask it temporarily
> > > > > mask_module_irq(true)
> > > > > clear_vio_status()
> > > > > // unmask
> > > > >  

Re: [PATCH v2] cpuidle: change enter_s2idle() prototype

2020-07-24 Thread Neal Liu
On Fri, 2020-07-24 at 13:20 +0200, Rafael J. Wysocki wrote:
> On Fri, Jul 24, 2020 at 12:24 PM Neal Liu  wrote:
> >
> > On Fri, 2020-07-24 at 11:57 +0200, Rafael J. Wysocki wrote:
> > > On Thu, Jul 23, 2020 at 9:07 PM Sami Tolvanen  
> > > wrote:
> > > >
> > > > On Mon, Jul 20, 2020 at 04:21:34PM +0800, Neal Liu wrote:
> > > > > Gentle ping on this patch.
> > > > >
> > > > >
> > > > > On Fri, 2020-07-10 at 11:08 +0800, Neal Liu wrote:
> > > > > > On Thu, 2020-07-09 at 14:18 +0200, Rafael J. Wysocki wrote:
> > > > > > > On Mon, Jul 6, 2020 at 5:13 AM Neal Liu  
> > > > > > > wrote:
> > > > > > > >
> > > > > > > > Control Flow Integrity(CFI) is a security mechanism that 
> > > > > > > > disallows
> > > > > > > > changes to the original control flow graph of a compiled binary,
> > > > > > > > making it significantly harder to perform such attacks.
> > > > > > > >
> > > > > > > > init_state_node() assign same function callback to different
> > > > > > > > function pointer declarations.
> > > > > > > >
> > > > > > > > static int init_state_node(struct cpuidle_state *idle_state,
> > > > > > > >const struct of_device_id *matches,
> > > > > > > >struct device_node *state_node) { ...
> > > > > > > > idle_state->enter = match_id->data; ...
> > > > > > > > idle_state->enter_s2idle = match_id->data; }
> > > > > > > >
> > > > > > > > Function declarations:
> > > > > > > >
> > > > > > > > struct cpuidle_state { ...
> > > > > > > > int (*enter) (struct cpuidle_device *dev,
> > > > > > > >   struct cpuidle_driver *drv,
> > > > > > > >   int index);
> > > > > > > >
> > > > > > > > void (*enter_s2idle) (struct cpuidle_device *dev,
> > > > > > > >   struct cpuidle_driver *drv,
> > > > > > > >   int index); };
> > > > > > > >
> > > > > > > > In this case, either enter() or enter_s2idle() would cause CFI 
> > > > > > > > check
> > > > > > > > failed since they use same callee.
> > > > > > >
> > > > > > > Can you please explain this in a bit more detail?
> > > > > > >
> > > > > > > As it stands, I don't understand the problem statement enough to 
> > > > > > > apply
> > > > > > > the patch.
> > > > > > >
> > > > > >
> > > > > > Okay, Let's me try to explain more details.
> > > > > > Control Flow Integrity(CFI) is a security mechanism that disallows
> > > > > > changes to the original control flow graph of a compiled binary, 
> > > > > > making
> > > > > > it significantly harder to perform such attacks.
> > > > > >
> > > > > > There are multiple control flow instructions that could be 
> > > > > > manipulated
> > > > > > by the attacker and subvert control flow. The target instructions 
> > > > > > that
> > > > > > use data to determine the actual destination.
> > > > > > - indirect jump
> > > > > > - indirect call
> > > > > > - return
> > > > > >
> > > > > > In this case, function prototype between caller and callee are 
> > > > > > mismatch.
> > > > > > Caller: (type A)funcA
> > > > > > Callee: (type A)funcB
> > > > > > Callee: (type C)funcC
> > > > > >
> > > > > > funcA calls funcB -> no problem
> > > > > > funcA calls funcC -> CFI check failed
> > > > > >
> > > > > > That's why we try to align function prototype.
> > > > > > Please feel free to feedback if you have any questions.
> > > >
> > > > I think you should include a

Re: [PATCH v2] cpuidle: change enter_s2idle() prototype

2020-07-24 Thread Neal Liu
On Fri, 2020-07-24 at 11:57 +0200, Rafael J. Wysocki wrote:
> On Thu, Jul 23, 2020 at 9:07 PM Sami Tolvanen  wrote:
> >
> > On Mon, Jul 20, 2020 at 04:21:34PM +0800, Neal Liu wrote:
> > > Gentle ping on this patch.
> > >
> > >
> > > On Fri, 2020-07-10 at 11:08 +0800, Neal Liu wrote:
> > > > On Thu, 2020-07-09 at 14:18 +0200, Rafael J. Wysocki wrote:
> > > > > On Mon, Jul 6, 2020 at 5:13 AM Neal Liu  wrote:
> > > > > >
> > > > > > Control Flow Integrity(CFI) is a security mechanism that disallows
> > > > > > changes to the original control flow graph of a compiled binary,
> > > > > > making it significantly harder to perform such attacks.
> > > > > >
> > > > > > init_state_node() assign same function callback to different
> > > > > > function pointer declarations.
> > > > > >
> > > > > > static int init_state_node(struct cpuidle_state *idle_state,
> > > > > >const struct of_device_id *matches,
> > > > > >struct device_node *state_node) { ...
> > > > > > idle_state->enter = match_id->data; ...
> > > > > > idle_state->enter_s2idle = match_id->data; }
> > > > > >
> > > > > > Function declarations:
> > > > > >
> > > > > > struct cpuidle_state { ...
> > > > > > int (*enter) (struct cpuidle_device *dev,
> > > > > >   struct cpuidle_driver *drv,
> > > > > >   int index);
> > > > > >
> > > > > > void (*enter_s2idle) (struct cpuidle_device *dev,
> > > > > >   struct cpuidle_driver *drv,
> > > > > >   int index); };
> > > > > >
> > > > > > In this case, either enter() or enter_s2idle() would cause CFI check
> > > > > > failed since they use same callee.
> > > > >
> > > > > Can you please explain this in a bit more detail?
> > > > >
> > > > > As it stands, I don't understand the problem statement enough to apply
> > > > > the patch.
> > > > >
> > > >
> > > > Okay, Let's me try to explain more details.
> > > > Control Flow Integrity(CFI) is a security mechanism that disallows
> > > > changes to the original control flow graph of a compiled binary, making
> > > > it significantly harder to perform such attacks.
> > > >
> > > > There are multiple control flow instructions that could be manipulated
> > > > by the attacker and subvert control flow. The target instructions that
> > > > use data to determine the actual destination.
> > > > - indirect jump
> > > > - indirect call
> > > > - return
> > > >
> > > > In this case, function prototype between caller and callee are mismatch.
> > > > Caller: (type A)funcA
> > > > Callee: (type A)funcB
> > > > Callee: (type C)funcC
> > > >
> > > > funcA calls funcB -> no problem
> > > > funcA calls funcC -> CFI check failed
> > > >
> > > > That's why we try to align function prototype.
> > > > Please feel free to feedback if you have any questions.
> >
> > I think you should include a better explanation in the commit message.
> > Perhaps something like this?
> >
> >   init_state_node assigns the same callback function to both enter and
> >   enter_s2idle despite mismatching function types, which trips indirect
> >   call checking with Control-Flow Integrity (CFI).
> >
> > > > > > Align function prototype of enter() since it needs return value for
> > > > > > some use cases. The return value of enter_s2idle() is no
> > > > > > need currently.
> > > > >
> > > > > So last time I requested you to document why ->enter_s2idle needs to
> > > > > return an int in the code, which has not been done.  Please do that.
> >
> > Rafael, are you happy with the commit message documenting the reason,
> > or would you prefer to also add a comment before enter_s2idle?
> 
> As I said before, it would be good to have a comment in the code as
> well or people will be wondering why it is necessary to return
> anything from that callback, because its return value is never used.
> 
> Thanks!

Is it okay to add these comments before enter_s2idle?

/*
 * Align function type since init_state_node assigns the same callback
 * function to both enter and enter_s2idle despite mismatching function
 * types, which trips indirect call checking with Control-Flow Integrity
 * (CFI).
 */
int (*enter_s2idle)(struct cpuidle_device *dev,
struct cpuidle_driver *drv,
int index);



Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-24 Thread Neal Liu
Hi Chun-Kuang,

On Fri, 2020-07-24 at 00:32 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月23日 週四 下午2:11寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Wed, 2020-07-22 at 22:25 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月22日 週三 上午11:49寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月21日 週二 下午12:00寫道:
> > > > > >
> > > > >
> > > > > > +
> > > > > > +/*
> > > > > > + * mtk_devapc_dump_vio_dbg - get the violation index and dump the 
> > > > > > full violation
> > > > > > + *   debug information.
> > > > > > + */
> > > > > > +static bool mtk_devapc_dump_vio_dbg(struct mtk_devapc_context 
> > > > > > *ctx, u32 vio_idx)
> > > > > > +{
> > > > > > +   u32 shift_bit;
> > > > > > +
> > > > > > +   if (check_vio_mask(ctx, vio_idx))
> > > > > > +   return false;
> > > > > > +
> > > > > > +   if (!check_vio_status(ctx, vio_idx))
> > > > > > +   return false;
> > > > > > +
> > > > > > +   shift_bit = get_shift_group(ctx, vio_idx);
> > > > > > +
> > > > > > +   if (sync_vio_dbg(ctx, shift_bit))
> > > > > > +   return false;
> > > > > > +
> > > > > > +   devapc_extract_vio_dbg(ctx);
> > > > >
> > > > > I think get_shift_group(), sync_vio_dbg(), and
> > > > > devapc_extract_vio_dbg() should be moved out of vio_idx for-loop (the
> > > > > loop in devapc_violation_irq()) because these three function is not
> > > > > related to vio_idx.
> > > > > Another question: when multiple vio_idx violation occur, vio_addr is
> > > > > related to which one vio_idx? The latest happened one?
> > > > >
> > > >
> > > > Actually, it's related to vio_idx. But we don't use it directly on these
> > > > function. I think below snip code might be better way to understand it.
> > > >
> > > > for (...)
> > > > {
> > > > check_vio_mask()
> > > > check_vio_status()
> > > >
> > > > // if get vio_idx, mask it temporarily
> > > > mask_module_irq(true)
> > > > clear_vio_status()
> > > >
> > > > // dump violation info
> > > > get_shift_group()
> > > > sync_vio_dbg()
> > > > devapc_extract_vio_dbg()
> > > >
> > > > // unmask
> > > > mask_module_irq(false)
> > > > }
> > >
> > > This snip code does not explain any thing. I could rewrite this code as:
> > >
> > > for (...)
> > > {
> > > check_vio_mask()
> > > check_vio_status()
> > >
> > > // if get vio_idx, mask it temporarily
> > > mask_module_irq(true)
> > > clear_vio_status()
> > > // unmask
> > > mask_module_irq(false)
> > > }
> > >
> > > // dump violation info
> > > get_shift_group()
> > > sync_vio_dbg()
> > > devapc_extract_vio_dbg()
> > >
> > > And my version is identical with your version, isn't it?
> >
> > Sorry, I did not explain it clearly. Let's me try again.
> > The reason why I put "dump violation info" between mask & unmask context
> > is because it has to stop interrupt first before dump violation info,
> > and then unmask it to prepare next violation.
> > These sequence guarantee that if multiple violation is triggered, we
> > still have information to debug.
> > If the code sequence in your version and multiple violation is
> > triggered, there might be no any information but keeps entering ISR.
> > Finally, system might be abnormal and watchdog timeout.
> > In this case, we still don't have any information to debug.
> 
> I still don't understand why no information to debug. For example when
> vio_idx 5, 10, 15 has violation,
> You would mask vio_i

Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-23 Thread Neal Liu
Hi Chun-Kuang,

On Wed, 2020-07-22 at 22:25 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月22日 週三 上午11:49寫道:
> >
> > Hi Chun-Kuang,
> >
> > On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月21日 週二 下午12:00寫道:
> > > >
> > >
> > > > +
> > > > +/*
> > > > + * mtk_devapc_dump_vio_dbg - get the violation index and dump the full 
> > > > violation
> > > > + *   debug information.
> > > > + */
> > > > +static bool mtk_devapc_dump_vio_dbg(struct mtk_devapc_context *ctx, 
> > > > u32 vio_idx)
> > > > +{
> > > > +   u32 shift_bit;
> > > > +
> > > > +   if (check_vio_mask(ctx, vio_idx))
> > > > +   return false;
> > > > +
> > > > +   if (!check_vio_status(ctx, vio_idx))
> > > > +   return false;
> > > > +
> > > > +   shift_bit = get_shift_group(ctx, vio_idx);
> > > > +
> > > > +   if (sync_vio_dbg(ctx, shift_bit))
> > > > +   return false;
> > > > +
> > > > +   devapc_extract_vio_dbg(ctx);
> > >
> > > I think get_shift_group(), sync_vio_dbg(), and
> > > devapc_extract_vio_dbg() should be moved out of vio_idx for-loop (the
> > > loop in devapc_violation_irq()) because these three function is not
> > > related to vio_idx.
> > > Another question: when multiple vio_idx violation occur, vio_addr is
> > > related to which one vio_idx? The latest happened one?
> > >
> >
> > Actually, it's related to vio_idx. But we don't use it directly on these
> > function. I think below snip code might be better way to understand it.
> >
> > for (...)
> > {
> > check_vio_mask()
> > check_vio_status()
> >
> > // if get vio_idx, mask it temporarily
> > mask_module_irq(true)
> > clear_vio_status()
> >
> > // dump violation info
> > get_shift_group()
> > sync_vio_dbg()
> > devapc_extract_vio_dbg()
> >
> > // unmask
> > mask_module_irq(false)
> > }
> 
> This snip code does not explain any thing. I could rewrite this code as:
> 
> for (...)
> {
> check_vio_mask()
> check_vio_status()
> 
> // if get vio_idx, mask it temporarily
> mask_module_irq(true)
> clear_vio_status()
> // unmask
> mask_module_irq(false)
> }
> 
> // dump violation info
> get_shift_group()
> sync_vio_dbg()
> devapc_extract_vio_dbg()
> 
> And my version is identical with your version, isn't it?

Sorry, I did not explain it clearly. Let's me try again.
The reason why I put "dump violation info" between mask & unmask context
is because it has to stop interrupt first before dump violation info,
and then unmask it to prepare next violation.
These sequence guarantee that if multiple violation is triggered, we
still have information to debug.
If the code sequence in your version and multiple violation is
triggered, there might be no any information but keeps entering ISR.
Finally, system might be abnormal and watchdog timeout.
In this case, we still don't have any information to debug.

> 
> >
> > About your question, vio_addr would be the first one.
> 
> So other vio_addr would be dropped? Or hardware would keep all
> vio_addr and you have some way to get all vio_addr?
> 

In this case, hardware will drop other violation info and keep the first
one until it been handled.

> >
> > > > +
> > > > +   return true;
> > > > +}
> > > > +
> > > > +/*
> > > > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) 
> > > > will dump
> > > > + *violation information including which master 
> > > > violates
> > > > + *access slave.
> > > > + */
> > > > +static irqreturn_t devapc_violation_irq(int irq_number,
> > > > +   struct mtk_devapc_context *ctx)
> > > > +{
> > > > +   u32 vio_idx;
> > > > +
> > > > +   for (vio_idx = 0; vio_idx < ctx->vio_idx_num; vio_idx++) {
> > > > +   if (!mtk_devapc_dump_vio_dbg(ctx, vio_idx))
> > > > +   continue;
> > > > +
> > > > + 

Re: [PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-21 Thread Neal Liu
Hi Chun-Kuang,

On Wed, 2020-07-22 at 07:21 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月21日 週二 下午12:00寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +static u32 get_shift_group(struct mtk_devapc_context *ctx, u32 vio_idx)
> 
> vio_idx is useless, so remove it.

Okay, I'll remove it in next patch.

> 
> > +{
> > +   u32 vio_shift_sta;
> > +   void __iomem *reg;
> > +
> > +   reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sta;
> > +   vio_shift_sta = readl(reg);
> > +
> > +   if (vio_shift_sta)
> > +   return __ffs(vio_shift_sta);
> > +
> > +   return 31;
> > +}
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * mtk_devapc_dump_vio_dbg - get the violation index and dump the full 
> > violation
> > + *   debug information.
> > + */
> > +static bool mtk_devapc_dump_vio_dbg(struct mtk_devapc_context *ctx, u32 
> > vio_idx)
> > +{
> > +   u32 shift_bit;
> > +
> > +   if (check_vio_mask(ctx, vio_idx))
> > +   return false;
> > +
> > +   if (!check_vio_status(ctx, vio_idx))
> > +   return false;
> > +
> > +   shift_bit = get_shift_group(ctx, vio_idx);
> > +
> > +   if (sync_vio_dbg(ctx, shift_bit))
> > +   return false;
> > +
> > +   devapc_extract_vio_dbg(ctx);
> 
> I think get_shift_group(), sync_vio_dbg(), and
> devapc_extract_vio_dbg() should be moved out of vio_idx for-loop (the
> loop in devapc_violation_irq()) because these three function is not
> related to vio_idx.
> Another question: when multiple vio_idx violation occur, vio_addr is
> related to which one vio_idx? The latest happened one?
> 

Actually, it's related to vio_idx. But we don't use it directly on these
function. I think below snip code might be better way to understand it.

for (...)
{
check_vio_mask()
check_vio_status()

// if get vio_idx, mask it temporarily
mask_module_irq(true)
clear_vio_status()

// dump violation info
get_shift_group()
sync_vio_dbg()
devapc_extract_vio_dbg()

// unmask
mask_module_irq(false)
}

About your question, vio_addr would be the first one.

> > +
> > +   return true;
> > +}
> > +
> > +/*
> > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) will 
> > dump
> > + *violation information including which master 
> > violates
> > + *access slave.
> > + */
> > +static irqreturn_t devapc_violation_irq(int irq_number,
> > +   struct mtk_devapc_context *ctx)
> > +{
> > +   u32 vio_idx;
> > +
> > +   for (vio_idx = 0; vio_idx < ctx->vio_idx_num; vio_idx++) {
> > +   if (!mtk_devapc_dump_vio_dbg(ctx, vio_idx))
> > +   continue;
> > +
> > +   /* Ensure that violation info are written before
> > +* further operations
> > +*/
> > +   smp_mb();
> > +
> > +   /*
> > +* Mask slave's irq before clearing vio status.
> > +* Must do it to avoid nested interrupt and prevent
> > +* unexpected behavior.
> > +*/
> > +   mask_module_irq(ctx, vio_idx, true);
> > +
> > +   clear_vio_status(ctx, vio_idx);
> > +
> > +   mask_module_irq(ctx, vio_idx, false);
> > +   }
> > +
> > +   return IRQ_HANDLED;
> > +}
> > +
> > +/*
> > + * start_devapc - initialize devapc status and start receiving interrupt
> > + *while devapc violation is triggered.
> > + */
> > +static int start_devapc(struct mtk_devapc_context *ctx)
> > +{
> > +   void __iomem *pd_vio_shift_sta_reg;
> > +   void __iomem *pd_apc_con_reg;
> > +   u32 vio_shift_sta;
> > +   

[PATCH v3 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-07-20 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..6c763f8
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


[PATCH v3 2/2] soc: mediatek: add mtk-devapc driver

2020-07-20 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 +
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  372 +
 drivers/soc/mediatek/mtk-devapc.h |   54 ++
 4 files changed, 436 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c
 create mode 100644 drivers/soc/mediatek/mtk-devapc.h

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..1397e98
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,372 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include "mtk-devapc.h"
+
+static u32 get_shift_group(struct mtk_devapc_context *ctx, u32 vio_idx)
+{
+   u32 vio_shift_sta;
+   void __iomem *reg;
+
+   reg = ctx->devapc_pd_base + ctx->offset->vio_shift_sta;
+   vio_shift_sta = readl(reg);
+
+   if (vio_shift_sta)
+   return __ffs(vio_shift_sta);
+
+   return 31;
+}
+
+static int check_vio_mask_sta(struct mtk_devapc_context *ctx, u32 module,
+ u32 offset)
+{
+   void __iomem *reg;
+   u32 value;
+
+   reg = ctx->devapc_pd_base + offset;
+   reg += 0x4 * VIO_MOD_TO_REG_IND(module);
+
+   value = readl(reg);
+
+   return ((value >> VIO_MOD_TO_REG_OFF(module)) & 0x1);
+}
+
+static int check_vio_mask(struct mtk_devapc_context *ctx, u32 module)
+{
+   return check_vio_mask_sta(ctx, module, ctx->offset->vio_mask);
+}
+
+static int check_vio_status(struct mtk_devapc_context *ctx, u32 module)
+{
+   return check_vio_mask_sta(ctx, module, ctx->offset->vio_sta);
+}
+
+static void clear_vio_status(struct mtk_devapc_context *ctx, u32 module)
+{
+   void __iomem *reg;
+
+   reg = ctx->devapc_pd_base + ctx->offset->vio_sta;
+   reg += 0x4 * VIO_MOD_TO_REG_IND(module);
+
+   writel(0x1 << VIO_MOD_TO_REG_OFF(module), reg);
+
+   if (check_vio_status(ctx, module))
+   dev_err(ctx->dev, "%s: Clear failed, module_index:0x%x\n",
+   __func__, module);
+}
+
+static void mask_module_irq(struct mtk_devapc_context *ctx, u32 module,
+   bool mask)
+{
+   void __iomem *reg;
+   u32 value;
+
+   reg = ctx->devapc_pd_base + ctx->offset->vio_mask;
+   reg += 0x4 * VIO_MOD_TO_REG_IND(module);
+
+   value = readl(reg);
+   if (mask)
+   value |= (0x1 << VIO_MOD_TO_REG_OFF(module));
+   else
+   value &= ~(0x1 << VIO_MOD_TO_REG_OFF(module));
+
+   writel(value, reg);
+}
+
+#define PHY_DEVAPC_TIMEOUT 0x1
+
+/*
+ * sync_vio_dbg - do "shift" mechansim" to get full violation information.
+ *shift mechanism is depends on devapc hardware design.
+ *Mediatek devapc set multiple slaves as a group. When 
violation
+ *is triggered, violation info is kept inside devapc hardware.
+ *Driver should do shift mechansim to "shift" full violation
+ *info to VIO_DBGs registers.
+ *
+ */
+static int sync_vi

[PATCH v3] Add MediaTek MT6779 devapc driver

2020-07-20 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further analysis 
or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v2:
- pass platform info through DT data.
- remove unnecessary function.
- remove slave_type because it always equals to 1 in current support SoC.
- use vio_idx_num instread of list all devices' index.
- add more comments to describe hardware behavior.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mtk-devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  58 +++
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 372 ++
 drivers/soc/mediatek/mtk-devapc.h |  54 +++
 5 files changed, 494 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c
 create mode 100644 drivers/soc/mediatek/mtk-devapc.h

-- 
2.18.0


Re: [PATCH v2] cpuidle: change enter_s2idle() prototype

2020-07-20 Thread Neal Liu
Gentle ping on this patch.


On Fri, 2020-07-10 at 11:08 +0800, Neal Liu wrote:
> On Thu, 2020-07-09 at 14:18 +0200, Rafael J. Wysocki wrote:
> > On Mon, Jul 6, 2020 at 5:13 AM Neal Liu  wrote:
> > >
> > > Control Flow Integrity(CFI) is a security mechanism that disallows
> > > changes to the original control flow graph of a compiled binary,
> > > making it significantly harder to perform such attacks.
> > >
> > > init_state_node() assign same function callback to different
> > > function pointer declarations.
> > >
> > > static int init_state_node(struct cpuidle_state *idle_state,
> > >const struct of_device_id *matches,
> > >struct device_node *state_node) { ...
> > > idle_state->enter = match_id->data; ...
> > > idle_state->enter_s2idle = match_id->data; }
> > >
> > > Function declarations:
> > >
> > > struct cpuidle_state { ...
> > > int (*enter) (struct cpuidle_device *dev,
> > >   struct cpuidle_driver *drv,
> > >   int index);
> > >
> > > void (*enter_s2idle) (struct cpuidle_device *dev,
> > >   struct cpuidle_driver *drv,
> > >   int index); };
> > >
> > > In this case, either enter() or enter_s2idle() would cause CFI check
> > > failed since they use same callee.
> > 
> > Can you please explain this in a bit more detail?
> > 
> > As it stands, I don't understand the problem statement enough to apply
> > the patch.
> > 
> 
> Okay, Let's me try to explain more details.
> Control Flow Integrity(CFI) is a security mechanism that disallows
> changes to the original control flow graph of a compiled binary, making
> it significantly harder to perform such attacks.
> 
> There are multiple control flow instructions that could be manipulated
> by the attacker and subvert control flow. The target instructions that
> use data to determine the actual destination.
> - indirect jump
> - indirect call
> - return
> 
> In this case, function prototype between caller and callee are mismatch.
> Caller: (type A)funcA
> Callee: (type A)funcB
> Callee: (type C)funcC
> 
> funcA calls funcB -> no problem
> funcA calls funcC -> CFI check failed
> 
> That's why we try to align function prototype.
> Please feel free to feedback if you have any questions.
> 
> > > Align function prototype of enter() since it needs return value for
> > > some use cases. The return value of enter_s2idle() is no
> > > need currently.
> > 
> > So last time I requested you to document why ->enter_s2idle needs to
> > return an int in the code, which has not been done.  Please do that.
> > 
> > > Signed-off-by: Neal Liu 
> > > ---
> > >  drivers/acpi/processor_idle.c   |6 --
> > >  drivers/cpuidle/cpuidle-tegra.c |8 +---
> > >  drivers/idle/intel_idle.c   |6 --
> > >  include/linux/cpuidle.h |6 +++---
> > >  4 files changed, 16 insertions(+), 10 deletions(-)
> > >
> > > diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
> > > index 75534c5..6ffb6c9 100644
> > > --- a/drivers/acpi/processor_idle.c
> > > +++ b/drivers/acpi/processor_idle.c
> > > @@ -655,8 +655,8 @@ static int acpi_idle_enter(struct cpuidle_device *dev,
> > > return index;
> > >  }
> > >
> > > -static void acpi_idle_enter_s2idle(struct cpuidle_device *dev,
> > > -  struct cpuidle_driver *drv, int index)
> > > +static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
> > > + struct cpuidle_driver *drv, int index)
> > >  {
> > > struct acpi_processor_cx *cx = per_cpu(acpi_cstate[index], 
> > > dev->cpu);
> > >
> > > @@ -674,6 +674,8 @@ static void acpi_idle_enter_s2idle(struct 
> > > cpuidle_device *dev,
> > > }
> > > }
> > > acpi_idle_do_entry(cx);
> > > +
> > > +   return 0;
> > >  }
> > >
> > >  static int acpi_processor_setup_cpuidle_cx(struct acpi_processor *pr,
> > > diff --git a/drivers/cpuidle/cpuidle-tegra.c 
> > > b/drivers/cpuidle/cpuidle-tegra.c
> > > index 1500458..a12fb14 100644
> > > --- a/drivers/cpuidle/cpuidle-tegra.c
> > >

Re: [PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-15 Thread Neal Liu
Hi Chun-Kuang,

On Thu, 2020-07-16 at 07:46 +0800, Chun-Kuang Hu wrote:
> HI, Neal:
> 
> Neal Liu  於 2020年7月9日 週四 下午5:13寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +/*
> > + * mtk_devapc_dump_vio_dbg - shift & dump the violation debug information.
> > + */
> > +static bool mtk_devapc_dump_vio_dbg(struct mtk_devapc_context *devapc_ctx,
> > +   int slave_type, int *vio_idx)
> > +{
> > +   const struct mtk_device_info **device_info;
> > +   u32 shift_bit;
> > +   int i;
> > +
> > +   device_info = devapc_ctx->device_info;
> > +
> > +   for (i = 0; i < get_vio_slave_num(slave_type); i++) {
> > +   *vio_idx = device_info[slave_type][i].vio_index;
> > +
> > +   if (check_vio_mask(devapc_ctx, slave_type, *vio_idx))
> > +   continue;
> 
> I guess if one vio_idx is masked, its status would never be true. If
> my guess is right, I think you could skip check_vio_mask() and
> directly check_vio_status().

No. Even if vio_idx is masked, vio_status will still raise when
violation is triggered.

> 
> > +
> > +   if (!check_vio_status(devapc_ctx, slave_type, *vio_idx))
> > +   continue;
> > +
> > +   shift_bit = get_shift_group(devapc_ctx, slave_type, 
> > *vio_idx);
> > +
> > +   if (!sync_vio_dbg(devapc_ctx, slave_type, shift_bit))
> > +   continue;
> > +
> > +   devapc_extract_vio_dbg(devapc_ctx, slave_type);
> > +
> > +   return true;
> 
> I think multiple vio_idx would violate at the same time, why just process one?

We process each vio_idx for each interrupt.
If there are multiple vio_idx is raised, it will trigger another
interrupt to handle it.

> 
> Regards,
> Chun-Kuang.
> 
> > +   }
> > +
> > +   return false;
> > +}



Re: [PATCH v2 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-07-13 Thread Neal Liu
On Fri, 2020-07-10 at 18:41 +0800, Matthias Brugger wrote:
> 
> On 09/07/2020 11:12, Neal Liu wrote:
> > Add bindings for mtk-devapc.
> > 
> > Signed-off-by: Neal Liu 
> > ---
> >   .../devicetree/bindings/soc/mediatek/devapc.yaml   |   82 
> > 
> >   1 file changed, 82 insertions(+)
> >   create mode 100644 
> > Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> > 
> > diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
> > b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> > new file mode 100644
> > index 000..f08243e
> > --- /dev/null
> > +++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
> > @@ -0,0 +1,82 @@
> > +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
> > +# # Copyright 2020 MediaTek Inc.
> > +%YAML 1.2
> > +---
> > +$id: 
> > "https://urldefense.com/v3/__http://devicetree.org/schemas/soc/mediatek/devapc.yaml*__;Iw!!CTRNKA9wMg0ARbw!1TwSriUtXU2ZjXdZkLODgduBZYDtG23ix3jRxqvN3bdfV29MaK0FUZ5OrDu7VDBq$
> >  "
> > +$schema: 
> > "https://urldefense.com/v3/__http://devicetree.org/meta-schemas/core.yaml*__;Iw!!CTRNKA9wMg0ARbw!1TwSriUtXU2ZjXdZkLODgduBZYDtG23ix3jRxqvN3bdfV29MaK0FUZ5OrNG2oecr$
> >  "
> > +
> > +title: MediaTek Device Access Permission Control driver
> > +
> > +description: |
> > +  MediaTek bus fabric provides TrustZone security support and data
> > +  protection to prevent slaves from being accessed by unexpected masters.
> > +  The security violation is logged and sent to the processor for further
> > +  analysis and countermeasures.
> > +
> > +maintainers:
> > +  - Neal Liu 
> > +
> > +properties:
> > +  compatible:
> > +enum:
> > +  - mediatek,mt6779-devapc
> > +
> > +  reg:
> > +description: The base address of devapc register bank
> > +maxItems: 1
> > +
> > +  interrupts:
> > +description: A single interrupt specifier
> > +maxItems: 1
> > +
> > +  clocks:
> > +description: Contains module clock source and clock names
> > +maxItems: 1
> > +
> > +  clock-names:
> > +description: Names of the clocks list in clocks property
> > +maxItems: 1
> > +
> > +  mediatek-slv_type_num:
> > +description: Numbers of slave type in mediatek platform
> > +maxItems: 1
> 
> This should go in the DT data, have a look for example at:
> https://urldefense.com/v3/__https://elixir.bootlin.com/linux/latest/source/drivers/soc/mediatek/mtk-pmic-wrap.c*L1842__;Iw!!CTRNKA9wMg0ARbw!1TwSriUtXU2ZjXdZkLODgduBZYDtG23ix3jRxqvN3bdfV29MaK0FUZ5OrGIX64pv$
>  
> and
> https://urldefense.com/v3/__https://elixir.bootlin.com/linux/latest/source/drivers/soc/mediatek/mtk-pmic-wrap.c*L1777__;Iw!!CTRNKA9wMg0ARbw!1TwSriUtXU2ZjXdZkLODgduBZYDtG23ix3jRxqvN3bdfV29MaK0FUZ5OrFN70av_$
>  
> 

Okay, I'll try to follow this example.

> > +
> > +  mediatek-vio_dbgs:
> > +description: The mask bit and start bit of devapc violation debug 
> > registers
> > +maxItems: 5
> > +
> 
> same here
> 
> > +  mediatek-pds_offset:
> > +description: The offset of devapc pds registers
> > +maxItems: 1
> 
> same here
> 
> > +
> > +required:
> > +  - compatible
> > +  - reg
> > +  - interrupts
> > +  - clocks
> > +  - clock-names
> > +  - mediatek-slv_type_num
> > +  - mediatek-vio_dbgs
> > +  - mediatek-pds_offset
> > +
> > +examples:
> > +  - |
> > +#include 
> > +#include 
> > +
> > +devapc: devapc@10207000 {
> > +  compatible = "mediatek,mt6779-devapc";
> > +  reg = <0x10207000 0x1000>;
> > +  interrupts = ;
> > +  clocks = <_ao CLK_INFRA_DEVICE_APC>;
> > +  clock-names = "devapc-infra-clock";
> > +
> > +  mediatek-slv_type_num = /bits/ 8 <1>;
> > +  mediatek-vio_dbgs = <0x 0x0>,
> > +  <0x003F 0x10>,
> > +  <0x0040 0x16>,
> > +  <0x0080 0x17>,
> > +  <0x0F00 0x18>;
> > +  mediatek-pds_offset = <0x0 0x400 0x900 0x904
> > + 0xF00 0xF10 0xF14 0xF20>;
> > +};
> > 
> 
> ___
> Linux-mediatek mailing list
> linux-media...@lists.infradead.org
> https://urldefense.com/v3/__http://lists.infradead.org/mailman/listinfo/linux-mediatek__;!!CTRNKA9wMg0ARbw!1TwSriUtXU2ZjXdZkLODgduBZYDtG23ix3jRxqvN3bdfV29MaK0FUZ5OrOXSJ2_W$
>  



Re: [PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-13 Thread Neal Liu
Hi Chun-Kuang,

On Mon, 2020-07-13 at 22:20 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月13日 週一 下午4:27寫道:
> >
> > Hi Chun-Kuang,
> >
> > Thanks for your review.
> >
> > On Fri, 2020-07-10 at 22:21 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月10日 週五 上午11:23寫道:
> > > >
> > > > Hi Chun-Kuang,
> > > >
> > > > Thanks for your review.
> > > >
> > > > On Thu, 2020-07-09 at 21:01 +0800, Chun-Kuang Hu wrote:
> > > > > Hi, Neal:
> > > > >
> > > > > Neal Liu  於 2020年7月9日 週四 下午5:13寫道:
> > > > > >
> > > > > > MediaTek bus fabric provides TrustZone security support and data
> > > > > > protection to prevent slaves from being accessed by unexpected
> > > > > > masters.
> > > > > > The security violation is logged and sent to the processor for
> > > > > > further analysis or countermeasures.
> > > > > >
> > > > > > Any occurrence of security violation would raise an interrupt, and
> > > > > > it will be handled by mtk-devapc driver. The violation
> > > > > > information is printed in order to find the murderer.
> > > > > >
> > > > > > Signed-off-by: Neal Liu 
> > > > >
> > > > > [snip]
> > > > >
> > > > > > +
> > > > > > +static u32 get_shift_group(struct mtk_devapc_context *devapc_ctx,
> > > > > > +  int slave_type, int vio_idx)
> > > > >
> > > > > vio_idx  is useless, so remove it.
> > > > >
> > > >
> > > > yes, my mistake. I'll remove it on next patch.
> > > >
> > > > > > +{
> > > > > > +   u32 vio_shift_sta;
> > > > > > +   void __iomem *reg;
> > > > > > +   int bit;
> > > > > > +
> > > > > > +   reg = mtk_devapc_pd_get(devapc_ctx, slave_type, 
> > > > > > VIO_SHIFT_STA, 0);
> > > > > > +   vio_shift_sta = readl(reg);
> > > > > > +
> > > > > > +   for (bit = 0; bit < 32; bit++) {
> > > > > > +   if ((vio_shift_sta >> bit) & 0x1)
> > > > > > +   break;
> > > > > > +   }
> > > > > > +
> > > > > > +   return bit;
> > > > > > +}
> > > > > > +
> > > > >
> > > > > [snip]
> > > > >
> > > > > > +
> > > > > > +/*
> > > > > > + * devapc_violation_irq - the devapc Interrupt Service Routine 
> > > > > > (ISR) will dump
> > > > > > + *   violation information including which 
> > > > > > master violates
> > > > > > + *   access slave.
> > > > > > + */
> > > > > > +static irqreturn_t devapc_violation_irq(int irq_number,
> > > > > > +   struct mtk_devapc_context 
> > > > > > *devapc_ctx)
> > > > > > +{
> > > > > > +   const struct mtk_device_info **device_info;
> > > > > > +   int slave_type_num;
> > > > > > +   int vio_idx = -1;
> > > > > > +   int slave_type;
> > > > > > +
> > > > > > +   slave_type_num = devapc_ctx->slave_type_num;
> > > > > > +   device_info = devapc_ctx->device_info;
> > > > > > +
> > > > > > +   for (slave_type = 0; slave_type < slave_type_num; 
> > > > > > slave_type++) {
> > > > >
> > > > > If slave_type_num is 1, I think the code should be simpler.
> > > >
> > > > slave_type_num is depends on DT data, it's not always 1.
> > >
> > > Please change commit title to "add mt6779 mtk-devapc driver". This
> > > patch is just for mt6779. If slave_type_num = 1 in mt6779, there is
> > > only one slave and we don't need a slave_type variable. Add
> > > slave_type_num in the patch of adding one SoC which has multiple
> > > slaves.
> >
> > If slave_type_num value is passed from DT data, could we still assume
>

Re: [PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-13 Thread Neal Liu
On Mon, 2020-07-13 at 13:16 +0200, Matthias Brugger wrote:
> 
> On 13/07/2020 09:45, Neal Liu wrote:
> > On Fri, 2020-07-10 at 14:14 +0200, Matthias Brugger wrote:
> >>
> > [snip]
> >>> +
> >>> +static int get_vio_slave_num(int slave_type)
> >>
> >> I have a hard time to understand the usefullness of this, can you please 
> >> explain.
> >>
> > 
> > The basic idea is to get total numbers of slaves. And we can use it to
> > scan all slaves which has been triggered violation.
> > I think I can pass it through DT data instead of using mtk_device_info
> > array. I'll send another patches to change it.
> > 
> >>> +{
> >>> + if (slave_type == 0)
> >>> + return ARRAY_SIZE(mtk_devices_infra);
> >>> +
> >>> + return 0;
> >>> +}
> >>> +
> >>> +static u32 get_shift_group(struct mtk_devapc_context *devapc_ctx,
> >>> +int slave_type, int vio_idx)
> >>> +{
> >>> + u32 vio_shift_sta;
> >>> + void __iomem *reg;
> >>> + int bit;
> >>> +
> >>> + reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_SHIFT_STA, 0);
> >>> + vio_shift_sta = readl(reg);
> >>> +
> >>> + for (bit = 0; bit < 32; bit++) {
> >>> + if ((vio_shift_sta >> bit) & 0x1) > +   break;
> >>> + }
> >>> +
> >>> + return bit;
> >>
> >> We return the first position (from the right) of the rigster with the bit 
> >> set to
> >> one. Correct?
> >> Can't we use __ffs() for this?
> > 
> > Yes, thanks for your reminds to use __ffs().
> > I'll revise it in next patches.
> > 
> >>
> >>> +}
> >>> +
> >>> +static int check_vio_mask_sta(struct mtk_devapc_context *devapc_ctx,
> >>> +   int slave_type, u32 module, int pd_reg_type)
> >>> +{
> >>> + u32 reg_index, reg_offset;
> >>> + void __iomem *reg;
> >>> + u32 value;
> >>> +
> >>> + VIO_MASK_STA_REG_GET(module);
> >>> +
> >>> + reg = mtk_devapc_pd_get(devapc_ctx, slave_type, pd_reg_type, reg_index);
> >>
> >> reg = mtk_devapc_pd_get(devapc_ctx, slave_type, pd_reg_type,
> >> VIO_MOD_TO_REG_IND(module));
> > 
> > Okay, I'll revise it in next patches.
> > 
> >>
> >>> + value = readl(reg);
> >>> +
> >>> + return ((value >> reg_offset) & 0x1);
> >>
> >> return ((value >> VIO_MOD_TO_REG_OFF(module)) & 0x1);
> > 
> > Okay, I'll revise it in next patches.
> > 
> >>
> >>> +}
> >>> +
> >>> +static int check_vio_mask(struct mtk_devapc_context *devapc_ctx, int 
> >>> slave_type,
> >>> +   u32 module)
> >>> +{
> >>> + return check_vio_mask_sta(devapc_ctx, slave_type, module, VIO_MASK);
> >>> +}
> >>> +
> >>> +static int check_vio_status(struct mtk_devapc_context *devapc_ctx,
> >>> + int slave_type, u32 module)
> >>> +{
> >>> + return check_vio_mask_sta(devapc_ctx, slave_type, module, VIO_STA);
> >>> +}
> >>> +
> >>> +static void clear_vio_status(struct mtk_devapc_context *devapc_ctx,
> >>> +  int slave_type, u32 module)
> >>> +{
> >>> + u32 reg_index, reg_offset;
> >>> + void __iomem *reg;
> >>> +
> >>> + VIO_MASK_STA_REG_GET(module);
> >>> +
> >>> + reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_STA, reg_index);
> >>> + writel(0x1 << reg_offset, reg);
> >>> +
> >>> + if (check_vio_status(devapc_ctx, slave_type, module))
> >>> + pr_err(PFX "%s: Clear failed, slave_type:0x%x, 
> >>> module_index:0x%x\n",
> >>> +__func__, slave_type, module);
> >>> +}
> >>> +
> >>> +static void mask_module_irq(struct mtk_devapc_context *devapc_ctx,
> >>> + int slave_type, u32 module, bool mask)
> >>> +{
> >>> + u32 reg_index, reg_offset;
> >>> + void __iomem *reg;
> >>> + u32 value;
> >>> +
> >>> + VIO_MASK_STA_REG_GET(module);
> >>> +
> >>> + reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_MASK, re

Re: [PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-13 Thread Neal Liu
Hi Chun-Kuang,

Thanks for your review.

On Fri, 2020-07-10 at 22:21 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月10日 週五 上午11:23寫道:
> >
> > Hi Chun-Kuang,
> >
> > Thanks for your review.
> >
> > On Thu, 2020-07-09 at 21:01 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年7月9日 週四 下午5:13寫道:
> > > >
> > > > MediaTek bus fabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violation is logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by mtk-devapc driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > >
> > > [snip]
> > >
> > > > +
> > > > +static u32 get_shift_group(struct mtk_devapc_context *devapc_ctx,
> > > > +  int slave_type, int vio_idx)
> > >
> > > vio_idx  is useless, so remove it.
> > >
> >
> > yes, my mistake. I'll remove it on next patch.
> >
> > > > +{
> > > > +   u32 vio_shift_sta;
> > > > +   void __iomem *reg;
> > > > +   int bit;
> > > > +
> > > > +   reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_SHIFT_STA, 
> > > > 0);
> > > > +   vio_shift_sta = readl(reg);
> > > > +
> > > > +   for (bit = 0; bit < 32; bit++) {
> > > > +   if ((vio_shift_sta >> bit) & 0x1)
> > > > +   break;
> > > > +   }
> > > > +
> > > > +   return bit;
> > > > +}
> > > > +
> > >
> > > [snip]
> > >
> > > > +
> > > > +/*
> > > > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) 
> > > > will dump
> > > > + *   violation information including which master 
> > > > violates
> > > > + *   access slave.
> > > > + */
> > > > +static irqreturn_t devapc_violation_irq(int irq_number,
> > > > +   struct mtk_devapc_context 
> > > > *devapc_ctx)
> > > > +{
> > > > +   const struct mtk_device_info **device_info;
> > > > +   int slave_type_num;
> > > > +   int vio_idx = -1;
> > > > +   int slave_type;
> > > > +
> > > > +   slave_type_num = devapc_ctx->slave_type_num;
> > > > +   device_info = devapc_ctx->device_info;
> > > > +
> > > > +   for (slave_type = 0; slave_type < slave_type_num; slave_type++) 
> > > > {
> > >
> > > If slave_type_num is 1, I think the code should be simpler.
> >
> > slave_type_num is depends on DT data, it's not always 1.
> 
> Please change commit title to "add mt6779 mtk-devapc driver". This
> patch is just for mt6779. If slave_type_num = 1 in mt6779, there is
> only one slave and we don't need a slave_type variable. Add
> slave_type_num in the patch of adding one SoC which has multiple
> slaves.

If slave_type_num value is passed from DT data, could we still assume
its value? Does it make sense to have this strong assumption?

I'm going to remove mtk_device_info struct array, and pass all SoC
specific data from DT.
Is it okay to keep slave_type_num as a variance?

> 
> >
> > >
> > > > +   if (!mtk_devapc_dump_vio_dbg(devapc_ctx, slave_type, 
> > > > _idx))
> > > > +   continue;
> > > > +
> > > > +   /* Ensure that violation info are written before
> > > > +* further operations
> > > > +*/
> > > > +   smp_mb();
> > > > +
> > > > +   mask_module_irq(devapc_ctx, slave_type, vio_idx, true);
> > >
> > > Why do you mask irq?
> >
> > It has to mask slave's irq before clear violation status.
> > It's one of hardware design.
> 
> If don't do this before clear_vio_status, what would happen? The clear
> would fail?

If we don't mask slave's irq before clear vio status, It might trig

Re: [PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-13 Thread Neal Liu
_u8(node, "mediatek-slv_type_num", _type_num))
> > +   return -ENXIO;
> > +
> > +   devapc_ctx->slave_type_num = slave_type_num;
> > +
> > +   size = slave_type_num * sizeof(void *);
> > +   devapc_ctx->devapc_pd_base = devm_kzalloc(>dev, size, GFP_KERNEL);
> > +   if (!devapc_ctx->devapc_pd_base)
> > +   return -ENOMEM;
> > +
> > +   size = slave_type_num * sizeof(struct mtk_device_info *);
> > +   devapc_ctx->device_info = devm_kzalloc(>dev, size, GFP_KERNEL);
> > +   if (!devapc_ctx->device_info)
> > +   return -ENOMEM;
> > +
> > +   for (i = 0; i < slave_type_num; i++) {
> > +   devapc_ctx->devapc_pd_base[i] = of_iomap(node, i);
> > +   if (!devapc_ctx->devapc_pd_base[i])
> > +   return -EINVAL;
> > +
> > +   if (i == 0)
> > +   devapc_ctx->device_info[i] = mtk_devices_infra;
> > +   }
> > +
> > +   size = sizeof(struct mtk_devapc_vio_info);
> > +   devapc_ctx->vio_info = devm_kzalloc(>dev, size, GFP_KERNEL);
> > +   if (!devapc_ctx->vio_info)
> > +   return -ENOMEM;
> > +
> > +   vio_dbgs_num = of_property_count_u32_elems(node, "mediatek-vio_dbgs");
> > +   if (vio_dbgs_num <= 0)
> > +   return -ENXIO;
> > +
> > +   size = (vio_dbgs_num / 2) * sizeof(struct mtk_devapc_vio_dbgs_desc);
> > +   devapc_ctx->vio_dbgs_desc = devm_kzalloc(>dev, size, GFP_KERNEL);
> > +   if (!devapc_ctx->vio_dbgs_desc)
> > +   return -ENOMEM;
> > +
> > +   for (i = 0; i < vio_dbgs_num / 2; i++) {
> > +   if (of_property_read_u32_index(node, "mediatek-vio_dbgs",
> > +  i * 2,
> > +  
> > _ctx->vio_dbgs_desc[i].mask))
> > +   return -ENXIO;
> > +
> > +   if (of_property_read_u32_index(node, "mediatek-vio_dbgs",
> > +  (i * 2) + 1,
> > +  
> > _ctx->vio_dbgs_desc[i].start_bit))
> > +   return -ENXIO;
> > +   }
> > +
> > +   pds_num = of_property_count_u32_elems(node, "mediatek-pds_offset");
> > +   if (pds_num <= 0)
> > +   return -ENXIO;
> > +
> > +   size = pds_num * sizeof(u32);
> > +   devapc_ctx->pds_offset = devm_kzalloc(>dev, size, GFP_KERNEL);
> > +   if (!devapc_ctx->pds_offset)
> > +   return -ENOMEM;
> > +
> > +   for (i = 0; i < pds_num; i++) {
> > +   if (of_property_read_u32_index(node, "mediatek-pds_offset", i,
> > +  _ctx->pds_offset[i]))
> > +   return -ENXIO;
> > +   }
> > +
> > +   devapc_irq = irq_of_parse_and_map(node, 0);
> > +   if (!devapc_irq)
> > +   return -EINVAL;
> > +
> > +   devapc_infra_clk = devm_clk_get(>dev, "devapc-infra-clock");
> > +   if (IS_ERR(devapc_infra_clk))
> > +   return -EINVAL;
> > +
> > +   if (clk_prepare_enable(devapc_infra_clk))
> > +   return -EINVAL;
> > +
> > +   start_devapc(devapc_ctx);
> > +
> > +   ret = devm_request_irq(>dev, devapc_irq,
> > +  (irq_handler_t)devapc_violation_irq,
> > +  IRQF_TRIGGER_NONE, "devapc", devapc_ctx);
> > +   if (ret)
> > +   return ret;
> > +
> > +   return 0;
> > +}
> > +
> > +static int mtk_devapc_remove(struct platform_device *dev)
> > +{
> > +   return 0;
> > +}
> > +
> > +static const struct of_device_id mtk_devapc_dt_match[] = {
> > +   { .compatible = "mediatek,mt6779-devapc" },
> > +   {},
> > +};
> > +
> > +static struct platform_driver mtk_devapc_driver = {
> > +   .probe = mtk_devapc_probe,
> > +   .remove = mtk_devapc_remove,
> > +   .driver = {
> > +   .name = KBUILD_MODNAME,
> > +   .of_match_table = mtk_devapc_dt_match,
> > +   },
> > +};
> > +
> > +module_platform_driver(mtk_devapc_driver);
> > +
> > +MODULE_DESCRIPTION("Mediatek Device APC Driver");
> > +MODULE_AUTHOR("Neal Liu ");
> > +MODULE_LICENSE("GPL");
> > diff --git a/drivers/soc/mediatek/mtk-devapc.h 
> > b/drivers/soc/mediatek/mtk-devapc.h
> > new file mode 100644
> > index 000..ab2cb

Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6779 driver

2020-07-13 Thread Neal Liu
[snip]
> >>> +/*
> >>> + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) 
> >>> will dump
> >>> + * violation information including which master 
> >>> violates
> >>> + * access slave.
> >>> + */
> >>> +static irqreturn_t devapc_violation_irq(int irq_number,
> >>> + struct mtk_devapc_context *devapc_ctx)
> >>> +{
> >>> + const struct mtk_device_info **device_info = devapc_ctx->device_info;
> >>> + int vio_idx = -1;
> >>> + int index = -1;
> >>> + int slave_type;
> >>> +
> >>> + for (slave_type = 0; slave_type < SLAVE_TYPE_NUM; slave_type++) {
> >>> + if (!mtk_devapc_dump_vio_dbg(devapc_ctx, slave_type, _idx,
> >>> +  ))
> >>> + continue;
> >>> +
> >>> + /* Ensure that violation info are written before
> >>> +  * further operations
> >>> +  */
> >>> + smp_mb();
> >>> +
> >>> + mask_module_irq(devapc_ctx, slave_type, vio_idx, true);
> >>> +
> >>> + clear_vio_status(devapc_ctx, slave_type, vio_idx);
> >>> +
> >>> + pr_info(PFX "Violation - slave_type:0x%x, sys_index:0x%x, 
> >>> ctrl_index:0x%x, vio_index:0x%x\n",
> >>> + slave_type,
> >>> + device_info[slave_type][index].sys_index,
> >>> + device_info[slave_type][index].ctrl_index,
> >>> + device_info[slave_type][index].vio_index);
> >>
> >> How will that then be used? Will there some kind of user-space daemon 
> >> which will
> >> parse the kernel log to see if a violation happens? What will it do with 
> >> this
> >> information?
> >>
> >> I still don't understand why we need to do that in the kernel instead of in
> >> TF-A. Can you please explain?
> >>
> > 
> > We would do different extra handle for different bus masters internally.
> 
> Does this mean that this is only one part of the whole story? Are you 
> planning 
> to hook into that code internally to implement the handling?
> In that we would need to support the whole thing in upstream. And this sounds 
> like you will need a new subsystem for bus firewall (or how you want to name 
> it). Which allows you to easily add support for other vendors SoCs.
> 

No, the extra handling is implemented by Mediatek proprietary drivers
which has no plan to upstream. And there is no need for first patch of
mtk-devapc driver.
Why do you think it need to support? and why it will need a new
subsystem?

The basic functionality of this driver is that it will handle violation
interrupt, and print violation information logs for further analysis.
Extra handling helps us to analyze violation more easily, but it's not a
basic functionality of it.

> > Basically, different bus masters have different debug mechanism.
> > And different customers have different severity about devapc violation.
> > For example, kernel exception, external exception, warning, don't
> > care,...
> > 
> > I list 2 reason why I put it in kernel instead of ATF.
> > 1. Rich OS such as Linux kernel has more debug mechanism and tools to
> > find murderer.
> 
> But you can access porgram counter from EL3 as well, so you could print all 
> the 
> info you need in TF-A.

For least privilege principle, there is no reason we should print all
the violation information in TF-A.

> 
> > 2. If interrupt has to be handled in ATF, GIC intr would be set as G0S
> > (Group 0 Secure). For our interrupt routing, G0S intr would be fiq. When
> > we handle it in EL3, it would mask all EL1 irq temporarily. We do not
> > treat devapc interrupt as such critical.
> 
> But you said "violation scenario is unexpected" so actually you don't expect 
> it 
> to happen.
> 
> > 
> > Doe it make sense? Or do you have any reason that it should be handled
> > in ATF?
> > 
> 
> My reasoning is that you bring a security mechanism into the kernel, which is 
> in 
> none-secure state. That's a contradiction.

There are two functionality for Mediatek devapc hardware.
1. permission control/protection
2. violation info

You can see that 1. is security mechanism for sure, and we put it in
TF-A.
But 2. is not "security" at all. it's for debugging purpose, we think
it's no any security concern to put it in NS-EL1.

> 
> Regards,
> Matthias
> 
[snip]



Re: [PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-09 Thread Neal Liu
Hi Chun-Kuang,

Thanks for your review.

On Thu, 2020-07-09 at 21:01 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年7月9日 週四 下午5:13寫道:
> >
> > MediaTek bus fabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violation is logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by mtk-devapc driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> 
> [snip]
> 
> > +
> > +static u32 get_shift_group(struct mtk_devapc_context *devapc_ctx,
> > +  int slave_type, int vio_idx)
> 
> vio_idx  is useless, so remove it.
> 

yes, my mistake. I'll remove it on next patch.

> > +{
> > +   u32 vio_shift_sta;
> > +   void __iomem *reg;
> > +   int bit;
> > +
> > +   reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_SHIFT_STA, 0);
> > +   vio_shift_sta = readl(reg);
> > +
> > +   for (bit = 0; bit < 32; bit++) {
> > +   if ((vio_shift_sta >> bit) & 0x1)
> > +   break;
> > +   }
> > +
> > +   return bit;
> > +}
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) will 
> > dump
> > + *   violation information including which master 
> > violates
> > + *   access slave.
> > + */
> > +static irqreturn_t devapc_violation_irq(int irq_number,
> > +   struct mtk_devapc_context 
> > *devapc_ctx)
> > +{
> > +   const struct mtk_device_info **device_info;
> > +   int slave_type_num;
> > +   int vio_idx = -1;
> > +   int slave_type;
> > +
> > +   slave_type_num = devapc_ctx->slave_type_num;
> > +   device_info = devapc_ctx->device_info;
> > +
> > +   for (slave_type = 0; slave_type < slave_type_num; slave_type++) {
> 
> If slave_type_num is 1, I think the code should be simpler.

slave_type_num is depends on DT data, it's not always 1.

> 
> > +   if (!mtk_devapc_dump_vio_dbg(devapc_ctx, slave_type, 
> > _idx))
> > +   continue;
> > +
> > +   /* Ensure that violation info are written before
> > +* further operations
> > +*/
> > +   smp_mb();
> > +
> > +   mask_module_irq(devapc_ctx, slave_type, vio_idx, true);
> 
> Why do you mask irq?

It has to mask slave's irq before clear violation status.
It's one of hardware design.

> 
> > +
> > +   clear_vio_status(devapc_ctx, slave_type, vio_idx);
> > +
> > +   mask_module_irq(devapc_ctx, slave_type, vio_idx, false);
> > +   }
> > +
> > +   return IRQ_HANDLED;
> > +}
> > +
> > +/*
> > + * start_devapc - initialize devapc status and start receiving interrupt
> > + *   while devapc violation is triggered.
> > + */
> 
> [snip]
> 
> > +
> > +struct mtk_device_info {
> > +   int sys_index;
> 
> Useless, so remove it.

We need to print it as our debug information.
But I did not apply it on this patch, I'll add it on next patch.

> 
> > +   int ctrl_index;
> 
> Ditto.
> 
> Regards,
> Chun-Kuang.
> 
> > +   int vio_index;
> > +};
> > +



Re: [PATCH v2] cpuidle: change enter_s2idle() prototype

2020-07-09 Thread Neal Liu
On Thu, 2020-07-09 at 14:18 +0200, Rafael J. Wysocki wrote:
> On Mon, Jul 6, 2020 at 5:13 AM Neal Liu  wrote:
> >
> > Control Flow Integrity(CFI) is a security mechanism that disallows
> > changes to the original control flow graph of a compiled binary,
> > making it significantly harder to perform such attacks.
> >
> > init_state_node() assign same function callback to different
> > function pointer declarations.
> >
> > static int init_state_node(struct cpuidle_state *idle_state,
> >const struct of_device_id *matches,
> >struct device_node *state_node) { ...
> > idle_state->enter = match_id->data; ...
> > idle_state->enter_s2idle = match_id->data; }
> >
> > Function declarations:
> >
> > struct cpuidle_state { ...
> > int (*enter) (struct cpuidle_device *dev,
> >   struct cpuidle_driver *drv,
> >   int index);
> >
> > void (*enter_s2idle) (struct cpuidle_device *dev,
> >   struct cpuidle_driver *drv,
> >   int index); };
> >
> > In this case, either enter() or enter_s2idle() would cause CFI check
> > failed since they use same callee.
> 
> Can you please explain this in a bit more detail?
> 
> As it stands, I don't understand the problem statement enough to apply
> the patch.
> 

Okay, Let's me try to explain more details.
Control Flow Integrity(CFI) is a security mechanism that disallows
changes to the original control flow graph of a compiled binary, making
it significantly harder to perform such attacks.

There are multiple control flow instructions that could be manipulated
by the attacker and subvert control flow. The target instructions that
use data to determine the actual destination.
- indirect jump
- indirect call
- return

In this case, function prototype between caller and callee are mismatch.
Caller: (type A)funcA
Callee: (type A)funcB
Callee: (type C)funcC

funcA calls funcB -> no problem
funcA calls funcC -> CFI check failed

That's why we try to align function prototype.
Please feel free to feedback if you have any questions.

> > Align function prototype of enter() since it needs return value for
> > some use cases. The return value of enter_s2idle() is no
> > need currently.
> 
> So last time I requested you to document why ->enter_s2idle needs to
> return an int in the code, which has not been done.  Please do that.
> 
> > Signed-off-by: Neal Liu 
> > ---
> >  drivers/acpi/processor_idle.c   |6 --
> >  drivers/cpuidle/cpuidle-tegra.c |8 +---
> >  drivers/idle/intel_idle.c   |6 --
> >  include/linux/cpuidle.h |6 +++---
> >  4 files changed, 16 insertions(+), 10 deletions(-)
> >
> > diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
> > index 75534c5..6ffb6c9 100644
> > --- a/drivers/acpi/processor_idle.c
> > +++ b/drivers/acpi/processor_idle.c
> > @@ -655,8 +655,8 @@ static int acpi_idle_enter(struct cpuidle_device *dev,
> > return index;
> >  }
> >
> > -static void acpi_idle_enter_s2idle(struct cpuidle_device *dev,
> > -  struct cpuidle_driver *drv, int index)
> > +static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
> > + struct cpuidle_driver *drv, int index)
> >  {
> > struct acpi_processor_cx *cx = per_cpu(acpi_cstate[index], 
> > dev->cpu);
> >
> > @@ -674,6 +674,8 @@ static void acpi_idle_enter_s2idle(struct 
> > cpuidle_device *dev,
> > }
> > }
> > acpi_idle_do_entry(cx);
> > +
> > +   return 0;
> >  }
> >
> >  static int acpi_processor_setup_cpuidle_cx(struct acpi_processor *pr,
> > diff --git a/drivers/cpuidle/cpuidle-tegra.c 
> > b/drivers/cpuidle/cpuidle-tegra.c
> > index 1500458..a12fb14 100644
> > --- a/drivers/cpuidle/cpuidle-tegra.c
> > +++ b/drivers/cpuidle/cpuidle-tegra.c
> > @@ -253,11 +253,13 @@ static int tegra_cpuidle_enter(struct cpuidle_device 
> > *dev,
> > return err ? -1 : index;
> >  }
> >
> > -static void tegra114_enter_s2idle(struct cpuidle_device *dev,
> > - struct cpuidle_driver *drv,
> > - int index)
> > +static int tegra114_enter_s2idle(struct cpuidle_device *dev,
> > +struct cpuidle_driver *drv,
> > +int in

[PATCH v2 2/2] soc: mediatek: add mtk-devapc driver

2020-07-09 Thread Neal Liu
MediaTek bus fabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violation is logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by mtk-devapc driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |9 +
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/mtk-devapc.c |  466 ++
 drivers/soc/mediatek/mtk-devapc.h |  670 +
 4 files changed, 1146 insertions(+)
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c
 create mode 100644 drivers/soc/mediatek/mtk-devapc.h

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..1177c98 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -17,6 +17,15 @@ config MTK_CMDQ
  time limitation, such as updating display configuration during the
  vblank.
 
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Say yes here to enable support for Mediatek Device APC driver.
+ This driver is mainly used to handle the violation which catches
+ unexpected transaction.
+ The violation information is logged for further analysis or
+ countermeasures.
+
 config MTK_INFRACFG
bool "MediaTek INFRACFG Support"
select REGMAP
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..abfd4ba 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += mtk-devapc.o
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/mtk-devapc.c 
b/drivers/soc/mediatek/mtk-devapc.c
new file mode 100644
index 000..11fa366
--- /dev/null
+++ b/drivers/soc/mediatek/mtk-devapc.c
@@ -0,0 +1,466 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include "mtk-devapc.h"
+
+/*
+ * mtk_devapc_pd_get - get devapc pd_types of register address.
+ *
+ * Returns the value of reg addr
+ */
+static void __iomem *mtk_devapc_pd_get(struct mtk_devapc_context *devapc_ctx,
+  int slave_type,
+  enum DEVAPC_PD_REG_TYPE pd_reg_type,
+  u32 reg_idx)
+{
+   void __iomem *reg;
+
+   reg = devapc_ctx->devapc_pd_base[slave_type] +
+   devapc_ctx->pds_offset[pd_reg_type];
+
+   if (pd_reg_type == VIO_MASK || pd_reg_type == VIO_STA)
+   reg += 0x4 * reg_idx;
+
+   return reg;
+}
+
+static int get_vio_slave_num(int slave_type)
+{
+   if (slave_type == 0)
+   return ARRAY_SIZE(mtk_devices_infra);
+
+   return 0;
+}
+
+static u32 get_shift_group(struct mtk_devapc_context *devapc_ctx,
+  int slave_type, int vio_idx)
+{
+   u32 vio_shift_sta;
+   void __iomem *reg;
+   int bit;
+
+   reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_SHIFT_STA, 0);
+   vio_shift_sta = readl(reg);
+
+   for (bit = 0; bit < 32; bit++) {
+   if ((vio_shift_sta >> bit) & 0x1)
+   break;
+   }
+
+   return bit;
+}
+
+static int check_vio_mask_sta(struct mtk_devapc_context *devapc_ctx,
+ int slave_type, u32 module, int pd_reg_type)
+{
+   u32 reg_index, reg_offset;
+   void __iomem *reg;
+   u32 value;
+
+   VIO_MASK_STA_REG_GET(module);
+
+   reg = mtk_devapc_pd_get(devapc_ctx, slave_type, pd_reg_type, reg_index);
+   value = readl(reg);
+
+   return ((value >> reg_offset) & 0x1);
+}
+
+static int check_vio_mask(struct mtk_devapc_context *devapc_ctx, int 
slave_type,
+ u32 module)
+{
+   return check_vio_mask_sta(devapc_ctx, slave_type, module, VIO_MASK);
+}
+
+static int check_vio_status(struct mtk_devapc_context *devapc_ctx,
+   int slave_type, u32 module)
+{
+   return check_vio_mask_sta(devapc_ctx, slave_type, module, VIO_STA);
+}
+
+static void clear_vio_status(struct mtk_devapc_context *devapc_ctx,
+int slave_type, u32 module)
+{
+   u32 reg_index, reg_offset;
+   void __iomem *reg;
+
+   VIO_MASK_STA_REG_GET(module);
+
+   reg = mtk_devapc_pd_get(devapc_ctx, slave_type, VIO_STA, reg_index);
+   writel(0x1 << reg_offset, reg);
+
+   if (check_vio_status(devapc_ctx, 

[PATCH v2] Add MediaTek MT6779 devapc driver

2020-07-09 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MediaTek bus fabric provides TrustZone security support and data protection
to prevent slaves from being accessed by unexpected masters.
The security violation is logged and sent to the processor for further
analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will
be handled by mtk-devapc driver.
The violation information is printed in order to find the murderer.

changes since v1:
- move SoC specific part to DT data.
- remove unnecessary boundary check.
- remove unnecessary data type declaration.
- use read_poll_timeout() instread of for loop polling.
- revise coding style elegantly.

*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for mtk-devapc
  soc: mediatek: add mtk-devapc driver

 .../bindings/soc/mediatek/devapc.yaml |  82 +++
 drivers/soc/mediatek/Kconfig  |   9 +
 drivers/soc/mediatek/Makefile |   1 +
 drivers/soc/mediatek/mtk-devapc.c | 466 
 drivers/soc/mediatek/mtk-devapc.h | 670 ++
 5 files changed, 1228 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
 create mode 100644 drivers/soc/mediatek/mtk-devapc.c
 create mode 100644 drivers/soc/mediatek/mtk-devapc.h

-- 
2.18.0


[PATCH v2 1/2] dt-bindings: devapc: add bindings for mtk-devapc

2020-07-09 Thread Neal Liu
Add bindings for mtk-devapc.

Signed-off-by: Neal Liu 
---
 .../devicetree/bindings/soc/mediatek/devapc.yaml   |   82 
 1 file changed, 82 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/soc/mediatek/devapc.yaml

diff --git a/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
new file mode 100644
index 000..f08243e
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc.yaml
@@ -0,0 +1,82 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek Device Access Permission Control driver
+
+description: |
+  MediaTek bus fabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violation is logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+  mediatek-slv_type_num:
+description: Numbers of slave type in mediatek platform
+maxItems: 1
+
+  mediatek-vio_dbgs:
+description: The mask bit and start bit of devapc violation debug registers
+maxItems: 5
+
+  mediatek-pds_offset:
+description: The offset of devapc pds registers
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+  - mediatek-slv_type_num
+  - mediatek-vio_dbgs
+  - mediatek-pds_offset
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+
+  mediatek-slv_type_num = /bits/ 8 <1>;
+  mediatek-vio_dbgs = <0x 0x0>,
+  <0x003F 0x10>,
+  <0x0040 0x16>,
+  <0x0080 0x17>,
+  <0x0F00 0x18>;
+  mediatek-pds_offset = <0x0 0x400 0x900 0x904
+ 0xF00 0xF10 0xF14 0xF20>;
+};
-- 
1.7.9.5


Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6779 driver

2020-07-07 Thread Neal Liu
Hi Matthias,

Thanks for your review.

On Mon, 2020-07-06 at 13:27 +0200, Matthias Brugger wrote:
> CC linux-mediatek
> 
> Please you ./scripts/get_maintainers.pl to find out to whom you should send 
> the
> series.

Yes, I already find out from get_maintainers.pl. But I forgot to add it
into cc list...

> 
> On 06/07/2020 11:28, Neal Liu wrote:
> > MT6779 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> > 
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6779 driver. The violation
> > information is printed in order to find the murderer.
> > 
> 
> Please describe in more detail how this HW works.

"devapc" means Device Access Permission Control.
This hardware can control which bus masters are allowed or disallowed to
access bus slaves. And it will generate interrupts if someone violates
the rules.
You can check binding for more details.

> 
> > Signed-off-by: Neal Liu 
> > ---
> 
> copying my comments from the last revision, which weren't answered and are not
> addressed here. If you are not OK with my sugguestions, no problem but please
> provide your arguments so that we can come up with a solution. Otherwise you 
> are
> just wasting your and my time:

Sorry for not replying your previous comments. I think your most
comments are really helpful and I already revised and applied it in this
patch.
Let's discuss the part I missed.

> 
> Please review your data structures and try to group the information in logical
> structs. For example I don't understand why we need mtk_devapc_context. It 
> seems
> to me that all the values in there are SoC specific.
> 

Yes, you are right. mtk_devapc_context dedicated to SoC specific.

> Why void __iomem *devapc_pd_base isn't part of the device_info?
> 

device_info stores slaves' info which are controlled by devapc.
devapc_pd_base stores devapc_pd based register which is used to control
and dump violation information.

> 
> 
> >  drivers/soc/mediatek/Kconfig|6 +
> >  drivers/soc/mediatek/Makefile   |1 +
> >  drivers/soc/mediatek/devapc/Kconfig |   17 +
> >  drivers/soc/mediatek/devapc/Makefile|   10 +
> >  drivers/soc/mediatek/devapc/devapc-mt6779.c |  
> > +++
> 
> From the answers of the last revision it seems that this driver will be used 
> for
> more then one SoC. So we should not name it devapc-mt6779.c but for example
> mtk-devapc.c.

Okay, we could use mtk-devapc.c for first patch. If we upstream next
SoC, then we could separate SoC specific part.

> 
> By the way, what does the devapc stands for? It's not clear from the commit
> message nor from the binding description.

It already described in binding title.
title: MediaTek MT6779 Device Access Permission Control driver

> 
> >  drivers/soc/mediatek/devapc/devapc-mt6779.h |   99 +++
> >  6 files changed, 1244 insertions(+)
> >  create mode 100644 drivers/soc/mediatek/devapc/Kconfig
> >  create mode 100644 drivers/soc/mediatek/devapc/Makefile
> >  create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6779.c
> >  create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6779.h
> > 
> > diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
> > index 59a56cd..2c9ad1f 100644
> > --- a/drivers/soc/mediatek/Kconfig
> > +++ b/drivers/soc/mediatek/Kconfig
> > @@ -51,4 +51,10 @@ config MTK_MMSYS
> >   Say yes here to add support for the MediaTek Multimedia
> >   Subsystem (MMSYS).
> >  
> > +menu "Security"
> > +
> > +source "drivers/soc/mediatek/devapc/Kconfig"
> > +
> > +endmenu # Security
> > +
> >  endmenu
> > diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
> > index 01f9f87..d6717a81 100644
> > --- a/drivers/soc/mediatek/Makefile
> > +++ b/drivers/soc/mediatek/Makefile
> > @@ -1,5 +1,6 @@
> >  # SPDX-License-Identifier: GPL-2.0-only
> >  obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
> > +obj-$(CONFIG_MTK_DEVAPC) += devapc/
> 
> Why do we need a new folder for the driver?

Currently, we don't need it. But once it support multiple platforms, we
would like to group it. Does it make sense?

> 
> >  obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
> >  obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
> >  obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
> > diff --git a/drivers/soc/mediatek/devapc/Kcon

Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6779 driver

2020-07-06 Thread Neal Liu
On Mon, 2020-07-06 at 20:32 -0700, Randy Dunlap wrote:
> On 7/6/20 8:30 PM, Neal Liu wrote:
> > Hi Randy,
> > 
> > Thanks for your review.
> > 
> > On Mon, 2020-07-06 at 09:13 -0700, Randy Dunlap wrote:
> >> On 7/6/20 2:28 AM, Neal Liu wrote:
> >>> diff --git a/drivers/soc/mediatek/devapc/Kconfig 
> >>> b/drivers/soc/mediatek/devapc/Kconfig
> >>> new file mode 100644
> >>> index 000..b0f7d0e
> >>> --- /dev/null
> >>> +++ b/drivers/soc/mediatek/devapc/Kconfig
> >>> @@ -0,0 +1,17 @@
> >>> +config MTK_DEVAPC
> >>> + tristate "Mediatek Device APC Support"
> >>> + help
> >>> +   Device APC is a HW IP controlling internal device security.
> >>
> >> preferably:   s/HW/hardware/
> >>
> >>> +   MediaTek bus frabric provides TrustZone security support and data
> >>
> >>   fabric
> >>
> >>> +   protection to prevent slaves from being accessed by unexpected
> >>> +   bus masters.
> >>> +   Device APC prevents malicious access to internal devices.
> >>> +
> >>> +config DEVAPC_MT6779
> >>> + tristate "Mediatek MT6779 Device APC driver"
> >>> + select MTK_DEVAPC
> >>> + help
> >>> +   Say yes here to enable support Mediatek MT6779 Device APC driver.
> >>
> >> support for Mediatek
> >>
> >>> +   This driver mainly used to handle the violation with 1 DEVAPC AO/PDs.
> >>
> >>  This driver is mainly used   
> >>
> >>  What is that meaningless string of chars? ^^^
> > 
> > I did not see any meaningless string of chars from my original patch.
> > Is there something wrong?
> 
> To someone who is reading the Kconfig help text but is unfamiliar with this 
> device,
> I would say that"1 DEVAPC AO/PDs"is not helpful 
> at all.

Got it, I'll try to make it more readable.

> 
> > [1] 
> > https://urldefense.com/v3/__https://lkml.org/lkml/2020/7/6/168__;!!CTRNKA9wMg0ARbw!0pAmVqUrtDEDPT-QkQENXso-_umOz2nbe-DDIlMb1sEsD57BaKtDZF47QFTfMSP-$
> >  
> > 
> >>
> >>> +   The violation information are logged for further analysis or
> >>
> >>is
> >>
> >>> +   countermeasures.
> >>
> >> thanks.
> > 
> 
> 
> thanks.



Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6779 driver

2020-07-06 Thread Neal Liu
Hi Randy,

Thanks for your review.

On Mon, 2020-07-06 at 09:13 -0700, Randy Dunlap wrote:
> On 7/6/20 2:28 AM, Neal Liu wrote:
> > diff --git a/drivers/soc/mediatek/devapc/Kconfig 
> > b/drivers/soc/mediatek/devapc/Kconfig
> > new file mode 100644
> > index 000..b0f7d0e
> > --- /dev/null
> > +++ b/drivers/soc/mediatek/devapc/Kconfig
> > @@ -0,0 +1,17 @@
> > +config MTK_DEVAPC
> > +   tristate "Mediatek Device APC Support"
> > +   help
> > + Device APC is a HW IP controlling internal device security.
> 
> preferably:   s/HW/hardware/
> 
> > + MediaTek bus frabric provides TrustZone security support and data
> 
>  fabric
> 
> > + protection to prevent slaves from being accessed by unexpected
> > + bus masters.
> > + Device APC prevents malicious access to internal devices.
> > +
> > +config DEVAPC_MT6779
> > +   tristate "Mediatek MT6779 Device APC driver"
> > +   select MTK_DEVAPC
> > +   help
> > + Say yes here to enable support Mediatek MT6779 Device APC driver.
> 
>support for Mediatek
> 
> > + This driver mainly used to handle the violation with 1 DEVAPC AO/PDs.
> 
> This driver is mainly used   
> 
> What is that meaningless string of chars? ^^^

I did not see any meaningless string of chars from my original patch.
Is there something wrong?

[1] https://lkml.org/lkml/2020/7/6/168

> 
> > + The violation information are logged for further analysis or
> 
>   is
> 
> > + countermeasures.
> 
> thanks.



[PATCH 2/2] soc: mediatek: devapc: add devapc-mt6779 driver

2020-07-06 Thread Neal Liu
MT6779 bus frabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violations are logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by devapc-mt6779 driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig|6 +
 drivers/soc/mediatek/Makefile   |1 +
 drivers/soc/mediatek/devapc/Kconfig |   17 +
 drivers/soc/mediatek/devapc/Makefile|   10 +
 drivers/soc/mediatek/devapc/devapc-mt6779.c |  +++
 drivers/soc/mediatek/devapc/devapc-mt6779.h |   99 +++
 6 files changed, 1244 insertions(+)
 create mode 100644 drivers/soc/mediatek/devapc/Kconfig
 create mode 100644 drivers/soc/mediatek/devapc/Makefile
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6779.c
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6779.h

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..2c9ad1f 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -51,4 +51,10 @@ config MTK_MMSYS
  Say yes here to add support for the MediaTek Multimedia
  Subsystem (MMSYS).
 
+menu "Security"
+
+source "drivers/soc/mediatek/devapc/Kconfig"
+
+endmenu # Security
+
 endmenu
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..d6717a81 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += devapc/
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/devapc/Kconfig 
b/drivers/soc/mediatek/devapc/Kconfig
new file mode 100644
index 000..b0f7d0e
--- /dev/null
+++ b/drivers/soc/mediatek/devapc/Kconfig
@@ -0,0 +1,17 @@
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Device APC is a HW IP controlling internal device security.
+ MediaTek bus frabric provides TrustZone security support and data
+ protection to prevent slaves from being accessed by unexpected
+ bus masters.
+ Device APC prevents malicious access to internal devices.
+
+config DEVAPC_MT6779
+   tristate "Mediatek MT6779 Device APC driver"
+   select MTK_DEVAPC
+   help
+ Say yes here to enable support Mediatek MT6779 Device APC driver.
+ This driver mainly used to handle the violation with 1 DEVAPC AO/PDs.
+ The violation information are logged for further analysis or
+ countermeasures.
diff --git a/drivers/soc/mediatek/devapc/Makefile 
b/drivers/soc/mediatek/devapc/Makefile
new file mode 100644
index 000..0336c1d
--- /dev/null
+++ b/drivers/soc/mediatek/devapc/Makefile
@@ -0,0 +1,10 @@
+# SPDX-License-Identifier: GPL-2.0
+
+ifeq ($(CONFIG_MTK_GCOV_KERNEL),y)
+GCOV_PROFILE := y
+endif
+
+obj-$(CONFIG_MTK_DEVAPC) := devapc.o
+
+# Platform
+devapc-$(CONFIG_DEVAPC_MT6779) += devapc-mt6779.o
diff --git a/drivers/soc/mediatek/devapc/devapc-mt6779.c 
b/drivers/soc/mediatek/devapc/devapc-mt6779.c
new file mode 100644
index 000..a28b9f3
--- /dev/null
+++ b/drivers/soc/mediatek/devapc/devapc-mt6779.c
@@ -0,0 +1, @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include "devapc-mt6779.h"
+
+static struct mtk_device_info mt6779_devices_infra[] = {
+   /* sys_idx, ctrl_idx, vio_idx */
+   /* 0 */
+   {0, 0, 0},
+   {0, 1, 1},
+   {0, 2, 2},
+   {0, 3, 3},
+   {0, 4, 4},
+   {0, 5, 5},
+   {0, 6, 6},
+   {0, 7, 7},
+   {0, 8, 8},
+   {0, 9, 9},
+
+   /* 10 */
+   {0, 10, 10},
+   {0, 11, 11},
+   {0, 12, 12},
+   {0, 13, 13},
+   {0, 14, 14},
+   {0, 15, 15},
+   {0, 16, 16},
+   {0, 17, 17},
+   {0, 18, 18},
+   {0, 19, 19},
+
+   /* 20 */
+   {0, 20, 20},
+   {0, 21, 21},
+   {0, 22, 22},
+   {0, 23, 23},
+   {0, 24, 24},
+   {0, 25, 25},
+   {0, 26, 26},
+   {0, 27, 27},
+   {0, 28, 28},
+   {0, 29, 29},
+
+   /* 30 */
+   {0, 30, 30},
+   {0, 31, 31},
+   {0, 32, 32},
+   {0, 33, 77},
+   {0, 34, 78},
+   {0, 35, 79},
+   {0, 35, 80},
+   {0, 37, 37},
+   {0, 38, 38},
+   {0, 39, 39},
+
+   /* 40 */
+   {0, 40, 40},
+   {0, 41, 41},
+   {0, 42, 42},
+   {0, 43, 43},
+   {0, 44, 44},
+   {0, 45, 45},
+   {0, 46, 46},
+   {0, 47, 47},
+   {0, 48, 48},
+   {0, 49, 49},

Add MediaTek MT6779 devapc driver

2020-07-06 Thread Neal Liu
These patch series introduce a MediaTek MT6779 devapc driver.

MT6779 bus frabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violations are logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt,
and it will be handled by devapc-mt6779 driver.
The violation information is printed in order to find the murderer.


*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for devapc-mt6779
  soc: mediatek: devapc: add devapc-mt6779 driver

 .../soc/mediatek/devapc/devapc-mt6779.yaml|   58 +
 drivers/soc/mediatek/Kconfig  |6 +
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/devapc/Kconfig   |   17 +
 drivers/soc/mediatek/devapc/Makefile  |   10 +
 drivers/soc/mediatek/devapc/devapc-mt6779.c   |  +
 drivers/soc/mediatek/devapc/devapc-mt6779.h   |   99 ++
 7 files changed, 1302 insertions(+)
 create mode 100644 
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6779.yaml
 create mode 100644 drivers/soc/mediatek/devapc/Kconfig
 create mode 100644 drivers/soc/mediatek/devapc/Makefile
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6779.c
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6779.h

-- 
2.18.0


[PATCH 1/2] dt-bindings: devapc: add bindings for devapc-mt6779

2020-07-06 Thread Neal Liu
Add bindings for MT6779 devapc.

Signed-off-by: Neal Liu 
---
 .../soc/mediatek/devapc/devapc-mt6779.yaml |   58 
 1 file changed, 58 insertions(+)
 create mode 100644 
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6779.yaml

diff --git 
a/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6779.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6779.yaml
new file mode 100644
index 000..b80f4d7
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6779.yaml
@@ -0,0 +1,58 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc/devapc-mt6779.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek MT6779 Device Access Permission Control driver
+
+description: |
+  MediaTek MT6779 bus frabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violations are logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6779-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 1
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+
+devapc: devapc@10207000 {
+  compatible = "mediatek,mt6779-devapc";
+  reg = <0x10207000 0x1000>;
+  interrupts = ;
+  clocks = <_ao CLK_INFRA_DEVICE_APC>;
+  clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


[PATCH v2] cpuidle: change enter_s2idle() prototype

2020-07-05 Thread Neal Liu
Control Flow Integrity(CFI) is a security mechanism that disallows
changes to the original control flow graph of a compiled binary,
making it significantly harder to perform such attacks.

init_state_node() assign same function callback to different
function pointer declarations.

static int init_state_node(struct cpuidle_state *idle_state,
   const struct of_device_id *matches,
   struct device_node *state_node) { ...
idle_state->enter = match_id->data; ...
idle_state->enter_s2idle = match_id->data; }

Function declarations:

struct cpuidle_state { ...
int (*enter) (struct cpuidle_device *dev,
  struct cpuidle_driver *drv,
  int index);

void (*enter_s2idle) (struct cpuidle_device *dev,
  struct cpuidle_driver *drv,
  int index); };

In this case, either enter() or enter_s2idle() would cause CFI check
failed since they use same callee.

Align function prototype of enter() since it needs return value for
some use cases. The return value of enter_s2idle() is no
need currently.

Signed-off-by: Neal Liu 
---
 drivers/acpi/processor_idle.c   |6 --
 drivers/cpuidle/cpuidle-tegra.c |8 +---
 drivers/idle/intel_idle.c   |6 --
 include/linux/cpuidle.h |6 +++---
 4 files changed, 16 insertions(+), 10 deletions(-)

diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
index 75534c5..6ffb6c9 100644
--- a/drivers/acpi/processor_idle.c
+++ b/drivers/acpi/processor_idle.c
@@ -655,8 +655,8 @@ static int acpi_idle_enter(struct cpuidle_device *dev,
return index;
 }
 
-static void acpi_idle_enter_s2idle(struct cpuidle_device *dev,
-  struct cpuidle_driver *drv, int index)
+static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
+ struct cpuidle_driver *drv, int index)
 {
struct acpi_processor_cx *cx = per_cpu(acpi_cstate[index], dev->cpu);
 
@@ -674,6 +674,8 @@ static void acpi_idle_enter_s2idle(struct cpuidle_device 
*dev,
}
}
acpi_idle_do_entry(cx);
+
+   return 0;
 }
 
 static int acpi_processor_setup_cpuidle_cx(struct acpi_processor *pr,
diff --git a/drivers/cpuidle/cpuidle-tegra.c b/drivers/cpuidle/cpuidle-tegra.c
index 1500458..a12fb14 100644
--- a/drivers/cpuidle/cpuidle-tegra.c
+++ b/drivers/cpuidle/cpuidle-tegra.c
@@ -253,11 +253,13 @@ static int tegra_cpuidle_enter(struct cpuidle_device *dev,
return err ? -1 : index;
 }
 
-static void tegra114_enter_s2idle(struct cpuidle_device *dev,
- struct cpuidle_driver *drv,
- int index)
+static int tegra114_enter_s2idle(struct cpuidle_device *dev,
+struct cpuidle_driver *drv,
+int index)
 {
tegra_cpuidle_enter(dev, drv, index);
+
+   return 0;
 }
 
 /*
diff --git a/drivers/idle/intel_idle.c b/drivers/idle/intel_idle.c
index f449584..b178da3 100644
--- a/drivers/idle/intel_idle.c
+++ b/drivers/idle/intel_idle.c
@@ -175,13 +175,15 @@ static __cpuidle int intel_idle(struct cpuidle_device 
*dev,
  * Invoked as a suspend-to-idle callback routine with frozen user space, frozen
  * scheduler tick and suspended scheduler clock on the target CPU.
  */
-static __cpuidle void intel_idle_s2idle(struct cpuidle_device *dev,
-   struct cpuidle_driver *drv, int index)
+static __cpuidle int intel_idle_s2idle(struct cpuidle_device *dev,
+  struct cpuidle_driver *drv, int index)
 {
unsigned long eax = flg2MWAIT(drv->states[index].flags);
unsigned long ecx = 1; /* break on interrupt flag */
 
mwait_idle_with_hints(eax, ecx);
+
+   return 0;
 }
 
 /*
diff --git a/include/linux/cpuidle.h b/include/linux/cpuidle.h
index ec2ef63..bee10c0 100644
--- a/include/linux/cpuidle.h
+++ b/include/linux/cpuidle.h
@@ -66,9 +66,9 @@ struct cpuidle_state {
 * suspended, so it must not re-enable interrupts at any point (even
 * temporarily) or attempt to change states of clock event devices.
 */
-   void (*enter_s2idle) (struct cpuidle_device *dev,
- struct cpuidle_driver *drv,
- int index);
+   int (*enter_s2idle)(struct cpuidle_device *dev,
+   struct cpuidle_driver *drv,
+   int index);
 };
 
 /* Idle State Flags */
-- 
1.7.9.5


[PATCH v2] cpuidle: Fix CFI failure

2020-07-05 Thread Neal Liu
changes since v1:
- add more description in commit message.

*** BLURB HERE ***

Neal Liu (1):
  cpuidle: change enter_s2idle() prototype

 drivers/acpi/processor_idle.c   | 6 --
 drivers/cpuidle/cpuidle-tegra.c | 8 +---
 drivers/idle/intel_idle.c   | 6 --
 include/linux/cpuidle.h | 6 +++---
 4 files changed, 16 insertions(+), 10 deletions(-)

-- 
2.18.0


Re: [PATCH] cpuidle: change enter_s2idle() prototype

2020-06-30 Thread Neal Liu
On Mon, 2020-06-29 at 17:17 +0200, Rafael J. Wysocki wrote:
> On Monday, June 29, 2020 11:05:40 AM CEST Neal Liu wrote:
> > Control Flow Integrity(CFI) is a security mechanism that disallows
> > changes to the original control flow graph of a compiled binary,
> > making it significantly harder to perform such attacks.
> > 
> > init_state_node() assigns same function pointer to idle_state->enter
> > and idle_state->enter_s2idle. This definitely causes CFI failure
> > when calling either enter() or enter_s2idle().
> > 
> > Align enter_s2idle() with enter() function prototype to fix CFI
> > failure.
> 
> That needs to be documented somewhere close to the definition of the
> callbacks in question.
> 
> Otherwise it is completely unclear why this is a good idea.
> 

The problem is, init_state_mode() assign same function callback to
different function pointer declarations.

static int init_state_node(struct cpuidle_state *idle_state,
   const struct of_device_id *matches,
   struct device_node *state_node)
{
...
idle_state->enter = match_id->data;
...
idle_state->enter_s2idle = match_id->data;
}

Function declarations:

struct cpuidle_state {
...
int (*enter)(struct cpuidle_device *dev,
struct cpuidle_driver *drv,
int index);

void (*enter_s2idle) (struct cpuidle_device *dev,
  struct cpuidle_driver *drv,
  int index);
};

In this case, either enter() or enter_s2idle() would cause CFI check
failed since they use same callee.

We try to align function prototype of enter() since it needs return
value for some use cases. The return value of enter_s2idle() is no need
currently.


> > Signed-off-by: Neal Liu 
> > ---
> >  drivers/acpi/processor_idle.c   |6 --
> >  drivers/cpuidle/cpuidle-tegra.c |8 +---
> >  drivers/idle/intel_idle.c   |6 --
> >  include/linux/cpuidle.h |6 +++---
> >  4 files changed, 16 insertions(+), 10 deletions(-)
> > 
> > diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
> > index 75534c5..6ffb6c9 100644
> > --- a/drivers/acpi/processor_idle.c
> > +++ b/drivers/acpi/processor_idle.c
> > @@ -655,8 +655,8 @@ static int acpi_idle_enter(struct cpuidle_device *dev,
> > return index;
> >  }
> >  
> > -static void acpi_idle_enter_s2idle(struct cpuidle_device *dev,
> > -  struct cpuidle_driver *drv, int index)
> > +static int acpi_idle_enter_s2idle(struct cpuidle_device *dev,
> > + struct cpuidle_driver *drv, int index)
> >  {
> > struct acpi_processor_cx *cx = per_cpu(acpi_cstate[index], dev->cpu);
> >  
> > @@ -674,6 +674,8 @@ static void acpi_idle_enter_s2idle(struct 
> > cpuidle_device *dev,
> > }
> > }
> > acpi_idle_do_entry(cx);
> > +
> > +   return 0;
> >  }
> >  
> >  static int acpi_processor_setup_cpuidle_cx(struct acpi_processor *pr,
> > diff --git a/drivers/cpuidle/cpuidle-tegra.c 
> > b/drivers/cpuidle/cpuidle-tegra.c
> > index 1500458..a12fb14 100644
> > --- a/drivers/cpuidle/cpuidle-tegra.c
> > +++ b/drivers/cpuidle/cpuidle-tegra.c
> > @@ -253,11 +253,13 @@ static int tegra_cpuidle_enter(struct cpuidle_device 
> > *dev,
> > return err ? -1 : index;
> >  }
> >  
> > -static void tegra114_enter_s2idle(struct cpuidle_device *dev,
> > - struct cpuidle_driver *drv,
> > - int index)
> > +static int tegra114_enter_s2idle(struct cpuidle_device *dev,
> > +struct cpuidle_driver *drv,
> > +int index)
> >  {
> > tegra_cpuidle_enter(dev, drv, index);
> > +
> > +   return 0;
> >  }
> >  
> >  /*
> > diff --git a/drivers/idle/intel_idle.c b/drivers/idle/intel_idle.c
> > index f449584..b178da3 100644
> > --- a/drivers/idle/intel_idle.c
> > +++ b/drivers/idle/intel_idle.c
> > @@ -175,13 +175,15 @@ static __cpuidle int intel_idle(struct cpuidle_device 
> > *dev,
> >   * Invoked as a suspend-to-idle callback routine with frozen user space, 
> > frozen
> >   * scheduler tick and suspended scheduler clock on the target CPU.
> >   */
> > -static __cpuidle void intel_idle_s2idle(struct cpuidle_device *dev,
> > -   struct cpuidle_driver *drv, int index)
> > +static __cpuidle int intel_idle_s2idle(struct cpuidle_device *dev

Re: [PATCH v2 1/2] dt-bindings: devapc: add bindings for devapc-mt6873

2020-06-30 Thread Neal Liu
On Mon, 2020-06-29 at 15:56 -0600, Rob Herring wrote:
> On Fri, 19 Jun 2020 17:41:59 +0800, Neal Liu wrote:
> > Add bindings for MT6873 devapc.
> > 
> > Signed-off-by: Neal Liu 
> > ---
> >  .../soc/mediatek/devapc/devapc-mt6873.yaml |   61 
> > 
> >  1 file changed, 61 insertions(+)
> >  create mode 100644 
> > Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml
> > 
> 
> 
> My bot found errors running 'make dt_binding_check' on your patch:
> 
> /builds/robherring/linux-dt-review/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml:
>  example-0: devapc@10207000:reg:0: [0, 270561280, 0, 4096] is too long
> /builds/robherring/linux-dt-review/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml:
>  example-0: devapc@10207000:reg:1: [0, 271007744, 0, 4096] is too long
> /builds/robherring/linux-dt-review/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml:
>  example-0: devapc@10207000:reg:2: [0, 271011840, 0, 4096] is too long
> /builds/robherring/linux-dt-review/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml:
>  example-0: devapc@10207000:reg:3: [0, 285343744, 0, 4096] is too long
> /builds/robherring/linux-dt-review/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml:
>  example-0: devapc@10207000:reg:4: [0, 270589952, 0, 4096] is too long
> 
> 
> See https://patchwork.ozlabs.org/patch/1312741
> 
> If you already ran 'make dt_binding_check' and didn't see the above
> error(s), then make sure dt-schema is up to date:
> 
> pip3 install git+https://github.com/devicetree-org/dt-schema.git@master 
> --upgrade
> 
> Please check and re-submit.
> 

I just pull the latest dt-schema from github, and it's still successful.
Is there any other clue for this difference?

$ PATH=~/virt_test/python36/bin:$PATH ARCH=arm64 make dt_binding_check
DT_SCHEMA_FILES=Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml
  CHKDT
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml
  DTC
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml
  CHECK
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.example.dt.yaml



Re: [PATCH v2 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-24 Thread Neal Liu
On Mon, 2020-06-22 at 12:05 +0200, Matthias Brugger wrote:
> 
> On 19/06/2020 11:42, Neal Liu wrote:
> > MT6873 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> > 
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6873 driver. The violation
> > information is printed in order to find the murderer.
> 
> Why don't we handle this in the TrustZone directly?

There is no reason that it should be handled in TrustZone only. And it
has no security issue to handle it in Normal World.

> 
> > 
> > Signed-off-by: Neal Liu 
> 
> This is a really big patch and it will be difficult to review.
> 
> Please do review the code and delete all the data structures that are not used
> (I already found two).
> 
> Please also check for code duplication (e.g. check_vio_mask and 
> check_vio_status
> are using 99% the same code).
> 
> Please review your data structures and try to group the information in logical
> structs. For example I don't understand why we need mtk_devapc_context. It 
> seems
> to me that all the values in there are SoC specific.
> 
> Think how you could split the driver up in several commits adding more
> functionality by each commit. With a good commit message it will be easier to
> understand what the code does.
> 

Thanks for your all suggestion, it's really helpful. I'll review again
and try to make patches more readable.

> On which SoC is the device used? I don't see any support for mt6873 in the
> kernel or the mailing list. Why do we want to support this driver upstream if
> it's not usable at all?
> 

Our mt6873 upstream tasks is on going, we'll send basic platform drivers
ASAP.

> Try to understand how the upstream kernel device model works. It looks to me 
> as
> if all the information is hardcoded. Would it make sense to pass some of the
> information via DT? Sorry for the generic question, but I hadn't had the time 
> to
> got through the whole driver to understand what it does.
> 
> Regards,
> Matthias
> 
> > ---
> >  drivers/soc/mediatek/Kconfig  |6 +
> >  drivers/soc/mediatek/Makefile |1 +
> >  drivers/soc/mediatek/devapc/Kconfig   |   25 +
> >  drivers/soc/mediatek/devapc/Makefile  |   13 +
> >  drivers/soc/mediatek/devapc/devapc-mt6873.c   | 1652 
> > +
> >  drivers/soc/mediatek/devapc/devapc-mt6873.h   |  111 ++
> >  drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.c |  756 ++
> >  drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.h |  182 +++
> >  8 files changed, 2746 insertions(+)
> >  create mode 100644 drivers/soc/mediatek/devapc/Kconfig
> >  create mode 100644 drivers/soc/mediatek/devapc/Makefile
> >  create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6873.c
> >  create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6873.h
> >  create mode 100644 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.c
> >  create mode 100644 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.h
> > 
> > diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
> > index 59a56cd..2c9ad1f 100644
> > --- a/drivers/soc/mediatek/Kconfig
> > +++ b/drivers/soc/mediatek/Kconfig
> > @@ -51,4 +51,10 @@ config MTK_MMSYS
> >   Say yes here to add support for the MediaTek Multimedia
> >   Subsystem (MMSYS).
> >  
> > +menu "Security"
> > +
> > +source "drivers/soc/mediatek/devapc/Kconfig"
> > +
> > +endmenu # Security
> > +
> >  endmenu
> > diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
> > index 01f9f87..d6717a81 100644
> > --- a/drivers/soc/mediatek/Makefile
> > +++ b/drivers/soc/mediatek/Makefile
> > @@ -1,5 +1,6 @@
> >  # SPDX-License-Identifier: GPL-2.0-only
> >  obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
> > +obj-$(CONFIG_MTK_DEVAPC) += devapc/
> >  obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
> >  obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
> >  obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
> > diff --git a/drivers/soc/mediatek/devapc/Kconfig 
> > b/drivers/soc/mediatek/devapc/Kconfig
> > new file mode 100644
> > index 000..9428360
> > --- /dev/null
> > +++ b/drivers/soc/mediatek/devapc/Kconfig
> > @@ -0,0 +1,25 @@
> > +config MTK_DEVAPC
> > +   tristate "Mediatek Device APC Support&

Re: Add MediaTek MT6873 devapc driver

2020-06-23 Thread Neal Liu
On Tue, 2020-06-09 at 11:32 -0600, Rob Herring wrote:
> On Tue, Jun 09, 2020 at 06:24:19PM +0800, Neal Liu wrote:
> > These patch series introduce a MediaTek MT6873 devapc driver.
> > 
> > MT6873 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> > 
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6873 driver. The violation
> > information is printed in order to find the murderer.
> 
> There's also a proposed driver with similar functionality[1]. Come up 
> with a common solution.
> 
> Rob
> 
> [1] 
> https://lore.kernel.org/linux-arm-kernel/20200128153806.7780-1-benjamin.gaign...@st.com/

Actually, Mediatek devapc HW do the similar things. But the real
"firewall" functionality is implemented in TrustZone instread of REE.
This devapc-mt6873 driver is mainly handled the violation.

Bus firewall framework seems not cover this parts.


Re: [PATCH v2 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-22 Thread Neal Liu
Hi Chun-Kuang,


On Sun, 2020-06-21 at 07:36 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年6月20日 週六 上午11:18寫道:
> >
> > Hi Chun-Kuang,
> >
> > Thanks for your quick feedback.
> >
> > On Sat, 2020-06-20 at 00:25 +0800, Chun-Kuang Hu wrote:
> > > Hi, Neal:
> > >
> > > Neal Liu  於 2020年6月19日 週五 下午6:01寫道:
> > > >
> > > > MT6873 bus frabric provides TrustZone security support and data
> > > > protection to prevent slaves from being accessed by unexpected
> > > > masters.
> > > > The security violations are logged and sent to the processor for
> > > > further analysis or countermeasures.
> > > >
> > > > Any occurrence of security violation would raise an interrupt, and
> > > > it will be handled by devapc-mt6873 driver. The violation
> > > > information is printed in order to find the murderer.
> > > >
> > > > Signed-off-by: Neal Liu 
> > > > ---
> > >
> > > [snip]
> > >
> > > > +
> > > > +/*
> > > > + * mtk_devapc_pd_get - get devapc pd_types of register address.
> > > > + *
> > > > + * Returns the value of reg addr
> > > > + */
> > > > +static void __iomem *mtk_devapc_pd_get(struct mtk_devapc_context 
> > > > *devapc_ctx,
> > > > +  int slave_type,
> > > > +  enum DEVAPC_PD_REG_TYPE 
> > > > pd_reg_type,
> > > > +  u32 index)
> > > > +{
> > > > +   struct mtk_devapc_vio_info *vio_info = 
> > > > devapc_ctx->soc->vio_info;
> > > > +   u32 slave_type_num = devapc_ctx->soc->slave_type_num;
> > > > +   const u32 *devapc_pds = devapc_ctx->soc->devapc_pds;
> > >
> > > devapc_pds = mt6873_devapc_pds;
> >
> > Are you saying all platform related variables & functions should assign
> > & call it directly in this common flow?
> > I don't think it's a good idea to go backwards since we already extract
> > the common out of it.
> 
> I think we should "do one thing in one patch". When you mix two things
> into one patch, how does reviewer know each modification belong to
> first thing or second thing? For supporting multiple SoC, the patches
> sequence look like this:
> 
> Patch 1: Add support SoC 1.
> Patch 2: Abstract function and variable for SoC 2.
> Patch 3: Add support SoC 2.
> Patch 4: Abstract function and variable for SoC 3.
> Patch 5: Add support SoC 3.
> Patch 6: Abstract function and variable for SoC 4.
> Patch 7: Add support SoC 4.
> 
> In patch 1, you should not do any thing about abstraction, but you
> want to merge patch 2, 4, 6 into this patch, so this patch's title
> should be "Add support SoC 1 and abstract function and varible for SoC
> 2, SoC 3, and SoC 4"
> 

Okay, I'll try to split driver to multiple patches for different
functionality. Thanks for suggestion.

> >
> > >
> > >
> > > > +   void __iomem *reg;
> > > > +
> > > > +   if (!devapc_pds)
> > >
> > > Never happen.
> > >
> > > > +   return NULL;
> > > > +
> > > > +   if ((slave_type < slave_type_num &&
> > > > +index < vio_info->vio_mask_sta_num[slave_type]) &&
> > > > +   pd_reg_type < PD_REG_TYPE_NUM) {
> > >
> > > Always true.
> > >
> > > > +   reg = devapc_ctx->devapc_pd_base[slave_type] +
> > > > +   devapc_pds[pd_reg_type];
> > > > +
> > > > +   if (pd_reg_type == VIO_MASK || pd_reg_type == VIO_STA)
> > > > +   reg += 0x4 * index;
> > > > +
> > > > +   } else {
> > > > +   pr_err(PFX "Out Of Boundary, 
> > > > slave_type:0x%x/pd_reg_type:0x%x/index:0x%x\n",
> > > > +  slave_type, pd_reg_type, index);
> > > > +   return NULL;
> > > > +   }
> > > > +
> > > > +   return reg;
> > > > +}
> > > > +
> > >
> > > [snip]
> > >
> > > > +
> > > > +/*
> > > > + * start_devapc - initialize devapc status and start receiving 
> > > >

Re: [PATCH v2 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-19 Thread Neal Liu
Hi Chun-Kuang,

Thanks for your quick feedback.

On Sat, 2020-06-20 at 00:25 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年6月19日 週五 下午6:01寫道:
> >
> > MT6873 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6873 driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +/*
> > + * mtk_devapc_pd_get - get devapc pd_types of register address.
> > + *
> > + * Returns the value of reg addr
> > + */
> > +static void __iomem *mtk_devapc_pd_get(struct mtk_devapc_context 
> > *devapc_ctx,
> > +  int slave_type,
> > +  enum DEVAPC_PD_REG_TYPE pd_reg_type,
> > +  u32 index)
> > +{
> > +   struct mtk_devapc_vio_info *vio_info = devapc_ctx->soc->vio_info;
> > +   u32 slave_type_num = devapc_ctx->soc->slave_type_num;
> > +   const u32 *devapc_pds = devapc_ctx->soc->devapc_pds;
> 
> devapc_pds = mt6873_devapc_pds;

Are you saying all platform related variables & functions should assign
& call it directly in this common flow?
I don't think it's a good idea to go backwards since we already extract
the common out of it.

> 
> 
> > +   void __iomem *reg;
> > +
> > +   if (!devapc_pds)
> 
> Never happen.
> 
> > +   return NULL;
> > +
> > +   if ((slave_type < slave_type_num &&
> > +index < vio_info->vio_mask_sta_num[slave_type]) &&
> > +   pd_reg_type < PD_REG_TYPE_NUM) {
> 
> Always true.
> 
> > +   reg = devapc_ctx->devapc_pd_base[slave_type] +
> > +   devapc_pds[pd_reg_type];
> > +
> > +   if (pd_reg_type == VIO_MASK || pd_reg_type == VIO_STA)
> > +   reg += 0x4 * index;
> > +
> > +   } else {
> > +   pr_err(PFX "Out Of Boundary, 
> > slave_type:0x%x/pd_reg_type:0x%x/index:0x%x\n",
> > +  slave_type, pd_reg_type, index);
> > +   return NULL;
> > +   }
> > +
> > +   return reg;
> > +}
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * start_devapc - initialize devapc status and start receiving interrupt
> > + *   while devapc violation is triggered.
> > + */
> > +static void start_devapc(struct mtk_devapc_context *devapc_ctx)
> > +{
> > +   u32 slave_type_num = devapc_ctx->soc->slave_type_num;
> > +   const struct mtk_device_info **device_info;
> > +   const struct mtk_device_num *ndevices;
> > +   void __iomem *pd_vio_shift_sta_reg;
> > +   void __iomem *pd_apc_con_reg;
> > +   int slave_type, i, vio_idx, index;
> > +   u32 vio_shift_sta;
> > +
> > +   ndevices = devapc_ctx->soc->ndevices;
> 
> ndevices = mtk6873_devices_num;
> 
> 
> > +
> > +   device_info = devapc_ctx->soc->device_info;
> > +
> > +   for (slave_type = 0; slave_type < slave_type_num; slave_type++) {
> > +   pd_apc_con_reg = mtk_devapc_pd_get(devapc_ctx, slave_type,
> > +  APC_CON, 0);
> > +   pd_vio_shift_sta_reg = mtk_devapc_pd_get(devapc_ctx, 
> > slave_type,
> > +VIO_SHIFT_STA, 0);
> > +
> > +   if (!pd_apc_con_reg || !pd_vio_shift_sta_reg || 
> > !device_info)
> > +   return;
> > +
> > +   /* Clear DEVAPC violation status */
> > +   writel(BIT(31), pd_apc_con_reg);
> > +
> > +   /* Clear violation shift status */
> > +   vio_shift_sta = readl(pd_vio_shift_sta_reg);
> > +   if (vio_shift_sta)
> > +   writel(vio_shift_sta, pd_vio_shift_sta_reg);
> > +
> > +   /* Clear type 2 violation status */
> > +   check_type2_vio_status(devapc_ctx, slave_type, _idx, 
> > );
> > +
> > +   /* Clear violation status */
> > +   for (i 

[PATCH v2 1/2] dt-bindings: devapc: add bindings for devapc-mt6873

2020-06-19 Thread Neal Liu
Add bindings for MT6873 devapc.

Signed-off-by: Neal Liu 
---
 .../soc/mediatek/devapc/devapc-mt6873.yaml |   61 
 1 file changed, 61 insertions(+)
 create mode 100644 
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml

diff --git 
a/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml 
b/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml
new file mode 100644
index 000..1deb7f6
--- /dev/null
+++ b/Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml
@@ -0,0 +1,61 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+# # Copyright 2020 MediaTek Inc.
+%YAML 1.2
+---
+$id: "http://devicetree.org/schemas/soc/mediatek/devapc/devapc-mt6873.yaml#;
+$schema: "http://devicetree.org/meta-schemas/core.yaml#;
+
+title: MediaTek MT6873 Device Access Permission Control driver
+
+description: |
+  MediaTek MT6873 bus frabric provides TrustZone security support and data
+  protection to prevent slaves from being accessed by unexpected masters.
+  The security violations are logged and sent to the processor for further
+  analysis and countermeasures.
+
+maintainers:
+  - Neal Liu 
+
+properties:
+  compatible:
+enum:
+  - mediatek,mt6873-devapc
+
+  reg:
+description: The base address of devapc register bank
+maxItems: 5
+
+  interrupts:
+description: A single interrupt specifier
+maxItems: 1
+
+  clocks:
+description: Contains module clock source and clock names
+maxItems: 1
+
+  clock-names:
+description: Names of the clocks list in clocks property
+maxItems: 1
+
+required:
+  - compatible
+  - reg
+  - interrupts
+  - clocks
+  - clock-names
+
+examples:
+  - |
+#include 
+#include 
+devapc: devapc@10207000 {
+compatible = "mediatek,mt6873-devapc";
+reg = <0 0x10207000 0 0x1000>,
+  <0 0x10274000 0 0x1000>,
+  <0 0x10275000 0 0x1000>,
+  <0 0x1102 0 0x1000>,
+  <0 0x1020e000 0 0x1000>;
+interrupts = ;
+clocks = < CLK_INFRA_DEVICE_APC>;
+clock-names = "devapc-infra-clock";
+};
-- 
1.7.9.5


Add MediaTek MT6873 devapc driver

2020-06-19 Thread Neal Liu
These patch series introduce a MediaTek MT6873 devapc driver.

MT6873 bus frabric provides TrustZone security support and data protection to 
prevent slaves from being accessed by unexpected masters.
The security violations are logged and sent to the processor for further 
analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and it will be 
handled by devapc-mt6873 driver. The violation information is printed in order 
to find the murderer.

changes since v1:
 - revise dt-bindings schema. (needs mt8192-clk.h to pass dt_binding_check)
 - remove debugging functions and make driver more simple.

*** BLURB HERE ***

Neal Liu (2):
  dt-bindings: devapc: add bindings for devapc-mt6873
  soc: mediatek: devapc: add devapc-mt6873 driver

 .../soc/mediatek/devapc/devapc-mt6873.yaml|   61 +
 drivers/soc/mediatek/Kconfig  |6 +
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/devapc/Kconfig   |   25 +
 drivers/soc/mediatek/devapc/Makefile  |   13 +
 drivers/soc/mediatek/devapc/devapc-mt6873.c   | 1652 +
 drivers/soc/mediatek/devapc/devapc-mt6873.h   |  111 ++
 .../soc/mediatek/devapc/devapc-mtk-multi-ao.c |  756 
 .../soc/mediatek/devapc/devapc-mtk-multi-ao.h |  182 ++
 9 files changed, 2807 insertions(+)
 create mode 100644 
Documentation/devicetree/bindings/soc/mediatek/devapc/devapc-mt6873.yaml
 create mode 100644 drivers/soc/mediatek/devapc/Kconfig
 create mode 100644 drivers/soc/mediatek/devapc/Makefile
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6873.c
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6873.h
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.c
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.h

-- 
2.18.0



[PATCH v2 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-19 Thread Neal Liu
MT6873 bus frabric provides TrustZone security support and data
protection to prevent slaves from being accessed by unexpected
masters.
The security violations are logged and sent to the processor for
further analysis or countermeasures.

Any occurrence of security violation would raise an interrupt, and
it will be handled by devapc-mt6873 driver. The violation
information is printed in order to find the murderer.

Signed-off-by: Neal Liu 
---
 drivers/soc/mediatek/Kconfig  |6 +
 drivers/soc/mediatek/Makefile |1 +
 drivers/soc/mediatek/devapc/Kconfig   |   25 +
 drivers/soc/mediatek/devapc/Makefile  |   13 +
 drivers/soc/mediatek/devapc/devapc-mt6873.c   | 1652 +
 drivers/soc/mediatek/devapc/devapc-mt6873.h   |  111 ++
 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.c |  756 ++
 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.h |  182 +++
 8 files changed, 2746 insertions(+)
 create mode 100644 drivers/soc/mediatek/devapc/Kconfig
 create mode 100644 drivers/soc/mediatek/devapc/Makefile
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6873.c
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mt6873.h
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.c
 create mode 100644 drivers/soc/mediatek/devapc/devapc-mtk-multi-ao.h

diff --git a/drivers/soc/mediatek/Kconfig b/drivers/soc/mediatek/Kconfig
index 59a56cd..2c9ad1f 100644
--- a/drivers/soc/mediatek/Kconfig
+++ b/drivers/soc/mediatek/Kconfig
@@ -51,4 +51,10 @@ config MTK_MMSYS
  Say yes here to add support for the MediaTek Multimedia
  Subsystem (MMSYS).
 
+menu "Security"
+
+source "drivers/soc/mediatek/devapc/Kconfig"
+
+endmenu # Security
+
 endmenu
diff --git a/drivers/soc/mediatek/Makefile b/drivers/soc/mediatek/Makefile
index 01f9f87..d6717a81 100644
--- a/drivers/soc/mediatek/Makefile
+++ b/drivers/soc/mediatek/Makefile
@@ -1,5 +1,6 @@
 # SPDX-License-Identifier: GPL-2.0-only
 obj-$(CONFIG_MTK_CMDQ) += mtk-cmdq-helper.o
+obj-$(CONFIG_MTK_DEVAPC) += devapc/
 obj-$(CONFIG_MTK_INFRACFG) += mtk-infracfg.o
 obj-$(CONFIG_MTK_PMIC_WRAP) += mtk-pmic-wrap.o
 obj-$(CONFIG_MTK_SCPSYS) += mtk-scpsys.o
diff --git a/drivers/soc/mediatek/devapc/Kconfig 
b/drivers/soc/mediatek/devapc/Kconfig
new file mode 100644
index 000..9428360
--- /dev/null
+++ b/drivers/soc/mediatek/devapc/Kconfig
@@ -0,0 +1,25 @@
+config MTK_DEVAPC
+   tristate "Mediatek Device APC Support"
+   help
+ Device APC is a kernel driver controlling internal device security.
+ If someone tries to access a device, which is not allowed by the
+ device, it cannot access the device and will get a violation
+ interrupt. Device APC prevents malicious access to internal devices.
+
+config DEVAPC_ARCH_MULTI
+   tristate "Mediatek Device APC driver architecture multi"
+   help
+ Say yes here to enable support Mediatek
+ Device APC driver which is based on Infra
+ architecture.
+ This architecture supports multiple Infra AO.
+
+config DEVAPC_MT6873
+   tristate "Mediatek MT6873 Device APC driver"
+   select MTK_DEVAPC
+   select DEVAPC_ARCH_MULTI
+   help
+ Say yes here to enable support Mediatek MT6873
+ Device APC driver.
+ This driver is combined with DEVAPC_ARCH_MULTI for
+ common handle flow.
diff --git a/drivers/soc/mediatek/devapc/Makefile 
b/drivers/soc/mediatek/devapc/Makefile
new file mode 100644
index 000..bd471f2
--- /dev/null
+++ b/drivers/soc/mediatek/devapc/Makefile
@@ -0,0 +1,13 @@
+# SPDX-License-Identifier: GPL-2.0
+
+ifeq ($(CONFIG_MTK_GCOV_KERNEL),y)
+GCOV_PROFILE := y
+endif
+
+obj-$(CONFIG_MTK_DEVAPC) := devapc.o
+
+# Core
+devapc-$(CONFIG_DEVAPC_ARCH_MULTI) += devapc-mtk-multi-ao.o
+
+# Platform
+devapc-$(CONFIG_DEVAPC_MT6873) += devapc-mt6873.o
diff --git a/drivers/soc/mediatek/devapc/devapc-mt6873.c 
b/drivers/soc/mediatek/devapc/devapc-mt6873.c
new file mode 100644
index 000..75a2140
--- /dev/null
+++ b/drivers/soc/mediatek/devapc/devapc-mt6873.c
@@ -0,0 +1,1652 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * Copyright (C) 2020 MediaTek Inc.
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include "devapc-mt6873.h"
+#include "devapc-mtk-multi-ao.h"
+
+static struct mtk_device_info mt6873_devices_infra[] = {
+   /* sys_idx, ctrl_idx, vio_idx */
+   /* 0 */
+   {0, 0, 0},
+   {0, 1, 1},
+   {0, 2, 2},
+   {0, 3, 3},
+   {0, 4, 4},
+   {0, 5, 5},
+   {0, 6, 6},
+   {0, 7, 7},
+   {0, 8, 8},
+   {0, 9, 9},
+
+   /* 10 */
+   {0, 10, 10},
+   {0, 11, 11},
+   {0, 12, 12},
+   {0, 13, 13},
+   {0, 14, 14},
+   {0, 15, 15},
+   {0, 16, 16},
+   {0, 17, 17},
+   {0, 18, 18},
+   {0, 19, 19},
+
+   /* 20 */
+   {0,

Re: Security Random Number Generator support

2020-06-18 Thread Neal Liu
Hi Marc,

On Thu, 2020-06-18 at 10:50 +0100, Marc Zyngier wrote:
> On 2020-06-03 08:54, Neal Liu wrote:
> 
> Hi Neal,
> 
> > Do you know which ARM expert could edict this standard?
> > Or is there any chance that we can make one? And be reviewed by
> > maintainers?
> 
> It appears that ARM just released a beta version of the spec at [1].
> 
> I'd encourage you (and anyone else) to have a look at it and provide 
> feedback to ARM.
> 
> Thanks,
> 
>  M.
> 
> [1] 
> https://developer.arm.com/-/media/Files/pdf/DEN0098-True_Random_Number_Generator_Firmware_Interface-1.0BET2.pdf

I also received this spec from ARM. I'll take a look and see if it meets
our needs.
Thanks for your sharing.


Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-16 Thread Neal Liu
Hi Chun-Kuang,


On Sat, 2020-06-13 at 07:20 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年6月9日 週二 下午6:25寫道:
> >
> > MT6873 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6873 driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> 
> [snip]
> 
> > +
> > +/*
> > + * sramrom_vio_handler - clean sramrom violation & print violation 
> > information
> > + *  for debugging.
> > + */
> > +static void sramrom_vio_handler(void)
> > +{
> > +   const struct mtk_sramrom_sec_vio_desc *sramrom_vios;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   struct arm_smccc_res res;
> > +   size_t sramrom_vio_sta;
> > +   int sramrom_vio;
> > +   u32 rw;
> > +
> > +   sramrom_vios = mtk_devapc_ctx->soc->sramrom_sec_vios;
> > +   vio_info = mtk_devapc_ctx->soc->vio_info;
> > +
> > +   arm_smccc_smc(MTK_SIP_KERNEL_CLR_SRAMROM_VIO,
> > + 0, 0, 0, 0, 0, 0, 0, );
> > +
> > +   sramrom_vio = res.a0;
> > +   sramrom_vio_sta = res.a1;
> > +   vio_info->vio_addr = res.a2;
> > +
> > +   if (sramrom_vio == SRAM_VIOLATION)
> > +   pr_info(PFX "%s, SRAM violation is triggered\n", __func__);
> > +   else if (sramrom_vio == ROM_VIOLATION)
> > +   pr_info(PFX "%s, ROM violation is triggered\n", __func__);
> > +   else
> > +   return;
> > +
> > +   vio_info->master_id = (sramrom_vio_sta & sramrom_vios->vio_id_mask)
> > +   >> sramrom_vios->vio_id_shift;
> > +   vio_info->domain_id = (sramrom_vio_sta & 
> > sramrom_vios->vio_domain_mask)
> > +   >> sramrom_vios->vio_domain_shift;
> > +   rw = (sramrom_vio_sta & sramrom_vios->vio_rw_mask) >>
> > +   sramrom_vios->vio_rw_shift;
> 
> I think some information, such as master_id, would be get in
> devapc_extract_vio_dbg(), you need not to get it here.

sramrom violation is from type2 slaves, and these kinds of slaves'
violation informations are stored in different registers than normal
slaves.
So we would check is it type2 violation or normal violation, and get
violation information from corresponding registers.

> > +
> > +   if (rw)
> > +   vio_info->write = 1;
> > +   else
> > +   vio_info->read = 1;
> > +
> > +   pr_info(PFX "%s: %s:0x%x, %s:0x%x, %s:%s, %s:0x%x\n",
> > +   __func__, "master_id", vio_info->master_id,
> > +   "domain_id", vio_info->domain_id,
> > +   "rw", rw ? "Write" : "Read",
> > +   "vio_addr", vio_info->vio_addr);
> > +}
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * devapc_violation_irq - the devapc Interrupt Service Routine (ISR) will 
> > dump
> > + *   violation information including which master 
> > violates
> > + *   access slave.
> > + */
> > +static irqreturn_t devapc_violation_irq(int irq_number, void *dev_id)
> > +{
> > +   u32 slave_type_num = mtk_devapc_ctx->soc->slave_type_num;
> 
> Don't make  mtk_devapc_ctx a global variable. You should allocate
> instance of  mtk_devapc_ctx in probe(), and pass  mtk_devapc_ctx to
> the last parameter of devm_request_irq(), and it would be the second
> parameter of irq handler.

Okay, I'll try to revise and upstream again.

> > +   const struct mtk_device_info **device_info;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   int slave_type, vio_idx, index;
> > +   const char *vio_master;
> > +   unsigned long flags;
> > +   bool normal;
> > +   u8 perm;
> > +
> > +   spin_lock_irqsave(_lock, flags);
> > +
> > +   device_info = mtk_devapc_ctx->soc->device_info;
> > +   vio_info = mtk_devapc_ctx->soc->vio_info;
> > +   normal = false;
> > +   vio_idx = -1;
> > +   index = -1;
&g

Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-16 Thread Neal Liu
Hi Chun-Kuang,

On Mon, 2020-06-15 at 23:51 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年6月9日 週二 下午6:25寫道:
> >
> > MT6873 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6873 driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +   {1, 0, 22, "MMSYS", true},
> > +   {1, 1, 23, "MMSYS_DISP", true},
> > +   {1, 2, 24, "SMI", true},
> > +   {1, 3, 25, "SMI", true},
> > +   {1, 4, 26, "SMI", true},
> > +   {1, 5, 27, "MMSYS_DISP", true},
> > +   {1, 6, 28, "MMSYS_DISP", true},
> > +
> > +   /* 30 */
> > +   {1, 7, 29, "MMSYS_DISP", true},
> > +   {1, 8, 30, "MMSYS_DISP", true},
> > +   {1, 9, 31, "MMSYS_DISP", true},
> > +   {1, 10, 32, "MMSYS_DISP", true},
> > +   {1, 11, 33, "MMSYS_DISP", true},
> > +   {1, 12, 34, "MMSYS_DISP", true},
> > +   {1, 13, 35, "MMSYS_DISP", true},
> > +   {1, 14, 36, "MMSYS_DISP", true},
> > +   {1, 15, 37, "MMSYS_DISP", true},
> > +   {1, 16, 38, "MMSYS_DISP", true},
> > +
> > +   /* 40 */
> > +   {1, 17, 39, "MMSYS_DISP", true},
> > +   {1, 18, 40, "MMSYS_DISP", true},
> > +   {1, 19, 41, "MMSYS_DISP", true},
> > +   {1, 20, 42, "MMSYS_DISP", true},
> > +   {1, 21, 43, "MMSYS_DISP", true},
> > +   {1, 22, 44, "MMSYS_DISP", true},
> 
> I think the device name, such as "MMSYS_DISP" does not help for debug.
> When DevAPC print "MMSYS_DISP" has error, how does us know that to do
> next? WHERE is the code may related to this error, and WHO should us
> to find help? I think we just need vio address. Using mt8173 for
> example, if the vio address is 0x1400d03c, we could find the device in
> mt8173.dtsi [1],
> 
> ovl1: ovl@1400d000 {
> compatible = "mediatek,mt8173-disp-ovl";
> reg = <0 0x1400d000 0 0x1000>;
> };
> 
> we could know error occur in ovl1, and we could find the compatible
> string "mediatek,mt8173-disp-ovl" in
> drivers/gpu/drm/mediatek/mtk_drm_drv.c, so we know WHERE is the code
> may related to this error. And we could find maintainer list [2] to
> find out the maintainer of this code:
> 
> DRM DRIVERS FOR MEDIATEK
> M: Chun-Kuang Hu 
> M: Philipp Zabel 
> L: dri-de...@lists.freedesktop.org
> S: Supported
> F: Documentation/devicetree/bindings/display/mediatek/
> F: drivers/gpu/drm/mediatek/
> 
> and we know find WHO for help.
> So I think we should drop device name and just print vio address is
> enough for debug.
> 
> [1] 
> https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/arch/arm64/boot/dts/mediatek/mt8173.dtsi?h=v5.8-rc1
> [2] 
> https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/MAINTAINERS?h=v5.8-rc1
> 

You are right. This is a way to find WHO can help this issue.
We integrated our internal debug system with device name, and it can
help us to find module owner automatically instead of searching dts and
source code manually.
But this kinds of debugging flow is not necessary for upstream. I'll try
to remove it.

> > +   {1, 23, 45, "MMSYS_MDP", true},
> > +   {1, 24, 46, "MMSYS_MDP", true},
> > +   {1, 25, 47, "MMSYS_MDP", true},
> > +   {1, 26, 48, "MMSYS_MDP", true},
> > +
> 
> [snip]
> 
> > +
> > +int mtk_devapc_probe(struct platform_device *pdev, struct mtk_devapc_soc 
> > *soc)
> > +{
> > +   struct device_node *node = pdev->dev.of_node;
> > +   u32 slave_type_num;
> > +   int slave_type;
> > +   int ret;
> > +
> > +   if (IS_ERR(node))
> > +   return -ENODEV;
> > +
> > +   mtk_devapc_ctx->soc = soc;
> > +   slave_type_num = mtk_devapc_ctx->soc->slave_type_num;
> > +
> > +   for (slave_type = 0; slave_type < slave_type_num; slave_type++) {
> > +   mtk_devapc_ctx->devapc_pd_base[slave_type] =
> &g

Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-16 Thread Neal Liu
Hi Chun-Kuang,

On Mon, 2020-06-15 at 22:17 +0800, Chun-Kuang Hu wrote:
> Chun-Kuang Hu  於 2020年6月15日 週一 下午10:14寫道:
> >
> > Hi, Neal:
> >
> > Neal Liu  於 2020年6月15日 週一 上午10:43寫道:
> > >
> > > Hi Chun-Kuang,
> > >
> > >
> > > On Sun, 2020-06-14 at 11:26 +0800, Chun-Kuang Hu wrote:
> > > > Hi, Neal:
> > > >
> > > > Neal Liu  於 2020年6月9日 週二 下午6:25寫道:
> > > > >
> > > > > MT6873 bus frabric provides TrustZone security support and data
> > > > > protection to prevent slaves from being accessed by unexpected
> > > > > masters.
> > > > > The security violations are logged and sent to the processor for
> > > > > further analysis or countermeasures.
> > > > >
> > > > > Any occurrence of security violation would raise an interrupt, and
> > > > > it will be handled by devapc-mt6873 driver. The violation
> > > > > information is printed in order to find the murderer.
> > > > >
> > > > > Signed-off-by: Neal Liu 
> > > > > ---
> > > >
> > > > [snip]
> > > >
> > > > > +
> > > > > +   /* 50 */
> > > > > +   {-1, -1, 50, "OOB_way_en", true},
> > > > > +   {-1, -1, 51, "OOB_way_en", true},
> > > > > +   {-1, -1, 52, "OOB_way_en", true},
> > > > > +   {-1, -1, 53, "OOB_way_en", true},
> > > > > +   {-1, -1, 54, "OOB_way_en", true},
> > > > > +   {-1, -1, 55, "OOB_way_en", true},
> > > > > +   {-1, -1, 56, "Decode_error", true},
> > > > > +   {-1, -1, 57, "Decode_error", true},
> > > > > +   {-1, -1, 58, "DISP_PWM", false},
> > > > > +   {-1, -1, 59, "IMP_IIC_WRAP", false},
> > > > > +
> > > > > +   /* 60 */
> > > > > +   {-1, -1, 60, "DEVICE_APC_PERI_PAR__AO", false},
> > > > > +   {-1, -1, 61, "DEVICE_APC_PERI_PAR_PDN", false},
> > > >
> > > > You does not process the item whose enable_vio_irq is false, so I
> > > > think you should remove these items and remove enable_vio_irq because
> > > > the rest item's enable_vio_irq would always be true.
> > >
> > > In some users, they can decide which slaves they want to enable or
> > > disable violation irq in different product. We remain this property for
> > > compatibility.
> >
> > I think in upstream version, you could still remove enable_vio_irq and
> > process all items. For downstream case, users could remove items they
> > does not interest in.

Okay, sounds good. I'll try to revise and upstream again.

> >
> > >
> > > >
> > > > > +};
> > > > > +
> > > > > +static struct mtk_device_num mtk6873_devices_num[] = {
> > > > > +   {SLAVE_TYPE_INFRA, VIO_SLAVE_NUM_INFRA},
> > > > > +   {SLAVE_TYPE_PERI, VIO_SLAVE_NUM_PERI},
> > > > > +   {SLAVE_TYPE_PERI2, VIO_SLAVE_NUM_PERI2},
> > > > > +   {SLAVE_TYPE_PERI_PAR, VIO_SLAVE_NUM_PERI_PAR},
> > > > > +};
> > > > > +
> > > > > +static struct PERIAXI_ID_INFO peri_mi_id_to_master[] = {
> > > > > +   {"THERM2",   { 0, 0, 0 } },
> > > > > +   {"SPM",  { 0, 1, 0 } },
> > > > > +   {"CCU",  { 0, 0, 1 } },
> > > > > +   {"THERM",{ 0, 1, 1 } },
> > > > > +   {"SPM_DRAMC",{ 1, 1, 0 } },
> > > >
> > > > The bits { 1, 1, 0 } equal to a number 0x3, I thiink you should use a
> > > > number instead of bits and everything would be more easy.
> > >
> > > We would like to keep it because the bit value contains more than 0/1,
> > > it might be '2' in some cases. '2' means it can be 0 or 1. This totally
> > > by hardware design & implementation.
> >
> > Upstream the patch that has dont-care-bits, otherwise, use a number for 
> > this.
> > Even there is dont-care-bits, I have a better way to process it. Here
> > is an example that has dont-care-bits:
> >
> > + {"Tinysys", { 0, 1, 0, 0, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0 } },
> >
> > I could use a { value, mask } pair for this case,
> >
> > value = 0x0002; /* value for care bits */
> > mask = 0x3c02; /* mask for care bits */
> 
> Sorry, this would be
> 
> mask = 0x3c0f; /* mask for care bits */
> 
> >
> > So the compare statement would be
> >
> > if ((bus_id & mask) == value)
> >
> > So you could get rid of the second for-loop and reduce the processing
> > time in irq handler.
> >

Great idea! I'll try to revise and upstream again.

> > Regards,
> > Chun-Kuang.



Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-14 Thread Neal Liu
Hi Chun-Kuang,


On Sun, 2020-06-14 at 11:26 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年6月9日 週二 下午6:25寫道:
> >
> > MT6873 bus frabric provides TrustZone security support and data
> > protection to prevent slaves from being accessed by unexpected
> > masters.
> > The security violations are logged and sent to the processor for
> > further analysis or countermeasures.
> >
> > Any occurrence of security violation would raise an interrupt, and
> > it will be handled by devapc-mt6873 driver. The violation
> > information is printed in order to find the murderer.
> >
> > Signed-off-by: Neal Liu 
> > ---
> 
> [snip]
> 
> > +
> > +   /* 50 */
> > +   {-1, -1, 50, "OOB_way_en", true},
> > +   {-1, -1, 51, "OOB_way_en", true},
> > +   {-1, -1, 52, "OOB_way_en", true},
> > +   {-1, -1, 53, "OOB_way_en", true},
> > +   {-1, -1, 54, "OOB_way_en", true},
> > +   {-1, -1, 55, "OOB_way_en", true},
> > +   {-1, -1, 56, "Decode_error", true},
> > +   {-1, -1, 57, "Decode_error", true},
> > +   {-1, -1, 58, "DISP_PWM", false},
> > +   {-1, -1, 59, "IMP_IIC_WRAP", false},
> > +
> > +   /* 60 */
> > +   {-1, -1, 60, "DEVICE_APC_PERI_PAR__AO", false},
> > +   {-1, -1, 61, "DEVICE_APC_PERI_PAR_PDN", false},
> 
> You does not process the item whose enable_vio_irq is false, so I
> think you should remove these items and remove enable_vio_irq because
> the rest item's enable_vio_irq would always be true.

In some users, they can decide which slaves they want to enable or
disable violation irq in different product. We remain this property for
compatibility.

> 
> > +};
> > +
> > +static struct mtk_device_num mtk6873_devices_num[] = {
> > +   {SLAVE_TYPE_INFRA, VIO_SLAVE_NUM_INFRA},
> > +   {SLAVE_TYPE_PERI, VIO_SLAVE_NUM_PERI},
> > +   {SLAVE_TYPE_PERI2, VIO_SLAVE_NUM_PERI2},
> > +   {SLAVE_TYPE_PERI_PAR, VIO_SLAVE_NUM_PERI_PAR},
> > +};
> > +
> > +static struct PERIAXI_ID_INFO peri_mi_id_to_master[] = {
> > +   {"THERM2",   { 0, 0, 0 } },
> > +   {"SPM",  { 0, 1, 0 } },
> > +   {"CCU",  { 0, 0, 1 } },
> > +   {"THERM",{ 0, 1, 1 } },
> > +   {"SPM_DRAMC",{ 1, 1, 0 } },
> 
> The bits { 1, 1, 0 } equal to a number 0x3, I thiink you should use a
> number instead of bits and everything would be more easy.

We would like to keep it because the bit value contains more than 0/1,
it might be '2' in some cases. '2' means it can be 0 or 1. This totally
by hardware design & implementation.

> > +};
> > +
> 
> [snip]
> 
> > +
> > +/*
> > + * mtk_devapc_vio_check - check violation shift status is raised or not.
> > + *
> > + * Returns the value of violation shift status reg
> > + */
> > +static void mtk_devapc_vio_check(int slave_type, int *shift_bit)
> > +{
> > +   u32 slave_type_num = mtk_devapc_ctx->soc->slave_type_num;
> > +   struct mtk_devapc_vio_info *vio_info;
> > +   u32 vio_shift_sta;
> > +   int i;
> > +
> > +   if (slave_type >= slave_type_num) {
> 
> This never happen, so remove it.

Indeed, thanks

> 
> > +   pr_err(PFX "%s: param check failed, %s:0x%x\n",
> > +  __func__, "slave_type", slave_type);
> > +   return;
> > +   }
> > +
> > +   vio_info = mtk_devapc_ctx->soc->vio_info;
> > +   vio_shift_sta = readl(mtk_devapc_pd_get(slave_type, VIO_SHIFT_STA, 
> > 0));
> > +
> > +   if (!vio_shift_sta) {
> > +   pr_info(PFX "violation is triggered before. %s:0x%x\n",
> > +   "shift_bit", *shift_bit);
> > +
> > +   } else if (vio_shift_sta & (0x1UL << *shift_bit)) {
> > +   pr_debug(PFX "%s: 0x%x is matched with %s:%d\n",
> > +"vio_shift_sta", vio_shift_sta,
> > +"shift_bit", *shift_bit);
> > +
> > +   } else {
> > +   pr_info(PFX "%s: 0x%x is not matched with %s:%d\n",
> > +   "vio_shift_sta", vio_shift_sta,
> > +   "shift_bit", *shift_bit);
> > +
> > +   for (i = 0; i < MOD_NO_IN_1_DEVAPC * 2; i++) {
>

Re: [PATCH 2/2] soc: mediatek: devapc: add devapc-mt6873 driver

2020-06-14 Thread Neal Liu
Hi Chun-Kuang,


On Fri, 2020-06-12 at 23:27 +0800, Chun-Kuang Hu wrote:
> Hi, Neal:
> 
> Neal Liu  於 2020年6月12日 週五 上午11:04寫道:
> >
> > Hi Chun-Kuang,
> >
> > [snip]
> > > > > > +/*
> > > > > > + * devapc_violation_irq - the devapc Interrupt Service Routine 
> > > > > > (ISR) will dump
> > > > > > + *   violation information including which 
> > > > > > master violates
> > > > > > + *   access slave.
> > > > > > + */
> > > > > > +static irqreturn_t devapc_violation_irq(int irq_number, void 
> > > > > > *dev_id)
> > > > > > +{
> > > > > > +   u32 slave_type_num = mtk_devapc_ctx->soc->slave_type_num;
> > > > > > +   const struct mtk_device_info **device_info;
> > > > > > +   struct mtk_devapc_vio_info *vio_info;
> > > > > > +   int slave_type, vio_idx, index;
> > > > > > +   const char *vio_master;
> > > > > > +   unsigned long flags;
> > > > > > +   bool normal;
> > > > > > +   u8 perm;
> > > > > > +
> > > > > > +   spin_lock_irqsave(_lock, flags);
> > > > > > +
> > > > > > +   device_info = mtk_devapc_ctx->soc->device_info;
> > > > > > +   vio_info = mtk_devapc_ctx->soc->vio_info;
> > > > > > +   normal = false;
> > > > > > +   vio_idx = -1;
> > > > > > +   index = -1;
> > > > > > +
> > > > > > +   /* There are multiple DEVAPC_PD */
> > > > > > +   for (slave_type = 0; slave_type < slave_type_num; 
> > > > > > slave_type++) {
> > > > > > +   if (!check_type2_vio_status(slave_type, _idx, 
> > > > > > ))
> > > > > > +   if (!mtk_devapc_dump_vio_dbg(slave_type, 
> > > > > > _idx,
> > > > > > +))
> > > > > > +   continue;
> > > > > > +
> > > > > > +   /* Ensure that violation info are written before
> > > > > > +* further operations
> > > > > > +*/
> > > > > > +   smp_mb();
> > > > > > +   normal = true;
> > > > > > +
> > > > > > +   mask_module_irq(slave_type, vio_idx, true);
> > > > > > +
> > > > > > +   if (clear_vio_status(slave_type, vio_idx))
> > > > > > +   pr_warn(PFX "%s, %s:0x%x, %s:0x%x\n",
> > > > > > +   "clear vio status failed",
> > > > > > +   "slave_type", slave_type,
> > > > > > +   "vio_index", vio_idx);
> > > > > > +
> > > > > > +   perm = get_permission(slave_type, index, 
> > > > > > vio_info->domain_id);
> > > > > > +
> > > > > > +   vio_master = mtk_devapc_ctx->soc->master_get
> > > > > > +   (vio_info->master_id,
> > > > > > +vio_info->vio_addr,
> > > > > > +slave_type,
> > > > > > +vio_info->shift_sta_bit,
> > > > > > +vio_info->domain_id);
> > > > >
> > > > > Call mt6873_bus_id_to_master() directly. For first patch, make things
> > > > > as simple as possible.
> > > >
> > > > In devapc_violation_irq() function, we use common flow to handle each
> > > > devapc violation on different platforms. The master_get() has different
> > > > implementation on different platforms, that why it called indirectly.
> > > >
> > > > Once we have new platform, we only have to update devapc-mt.c
> > > > instead of common handler flow.
> > >
> > > You just upstream one SoC now, so I have no information of 2nd SoC.
> > > Without the 2nd SoC, how do we know what is common and what is SoC 
> > > special?
> > > So t

  1   2   >