dev-arm: Implement System Security Control registers

This block of system registers is part of the N1 SDP [1]

[1]: https://developer.arm.com/documentation/101489/0000/\
    Programmers-model/System-Security-Control-registers

Change-Id: I2ecf5cd247bd68eddcd359e91f3954070dbffaa8
Signed-off-by: Giacomo Travaglini <giacomo.travaglini@arm.com>
Reviewed-by: Richard Cooper <richard.cooper@arm.com>
Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/64951
Maintainer: Andreas Sandberg <andreas.sandberg@arm.com>
Tested-by: kokoro <noreply+kokoro@google.com>
Reviewed-by: Andreas Sandberg <andreas.sandberg@arm.com>
diff --git a/src/dev/arm/RealView.py b/src/dev/arm/RealView.py
index 4a6c67e..41e1bcf 100644
--- a/src/dev/arm/RealView.py
+++ b/src/dev/arm/RealView.py
@@ -412,6 +412,32 @@
         yield node
 
 
+class SysSecCtrl(BasicPioDevice):
+    """
+    System Security Control registers. Taken from:
+        Arm Neoverse N1 System Development Platform - TRM - Version 0.0
+        Document ID: 101489_0000_02_en
+    """
+
+    type = "SysSecCtrl"
+    cxx_header = "dev/arm/ssc.hh"
+    cxx_class = "gem5::SysSecCtrl"
+
+    ssc_dbgcfg_stat = Param.Unsigned(
+        0x00010000, "Debug authentication configuration status"
+    )
+    ssc_version = Param.Unsigned(0x100417B0, "Version register")
+    ssc_pid0 = Param.Unsigned(0x44, "Peripheral ID0 register")
+    ssc_pid1 = Param.Unsigned(0xB8, "Peripheral ID1 register")
+    ssc_pid2 = Param.Unsigned(0xB, "Peripheral ID2 register")
+    ssc_pid4 = Param.Unsigned(0x4, "Peripheral ID4 register")
+
+    compid0 = Param.Unsigned(0x0D, "Component ID0 register")
+    compid1 = Param.Unsigned(0xF0, "Component ID1 register")
+    compid2 = Param.Unsigned(0x5, "Component ID2 register")
+    compid3 = Param.Unsigned(0xB1, "Component ID3 register")
+
+
 class AmbaFake(AmbaPioDevice):
     type = "AmbaFake"
     cxx_header = "dev/arm/amba_fake.hh"
diff --git a/src/dev/arm/SConscript b/src/dev/arm/SConscript
index f7e9c76..0a68e48 100644
--- a/src/dev/arm/SConscript
+++ b/src/dev/arm/SConscript
@@ -54,7 +54,7 @@
     'GenericArmPciHost', 'RealViewCtrl', 'RealViewOsc',
     'RealViewTemperatureSensor', 'AmbaFake', 'Pl011', 'Sp804', 'Sp805',
     'GenericWatchdog', 'CpuLocalTimer', 'PL031', 'Pl050', 'Pl111', 'HDLcd',
-    'FVPBasePwrCtrl', 'RealView'],
+    'FVPBasePwrCtrl', 'RealView', 'SysSecCtrl'],
     enums=['ArmPciIntRouting'], tags='arm isa')
 SimObject('SMMUv3.py', sim_objects=['SMMUv3DeviceInterface', 'SMMUv3'],
     tags='arm isa')
@@ -92,6 +92,7 @@
 Source('smmu_v3_proc.cc', tags='arm isa');
 Source('smmu_v3_deviceifc.cc', tags='arm isa');
 Source('smmu_v3_transl.cc', tags='arm isa');
+Source('ssc.cc', tags='arm isa');
 Source('timer_sp804.cc', tags='arm isa')
 Source('watchdog_generic.cc', tags='arm isa')
 Source('watchdog_sp805.cc', tags='arm isa')
diff --git a/src/dev/arm/ssc.cc b/src/dev/arm/ssc.cc
new file mode 100644
index 0000000..4a57647
--- /dev/null
+++ b/src/dev/arm/ssc.cc
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2022 Arm Limited
+ * All rights reserved
+ *
+ * The license below extends only to copyright in the software and shall
+ * not be construed as granting a license to any other intellectual
+ * property including but not limited to intellectual property relating
+ * to a hardware implementation of the functionality of the software
+ * licensed hereunder.  You may use the software subject to the license
+ * terms below provided that you ensure that this notice is replicated
+ * unmodified and in its entirety in all distributions of the software,
+ * modified or unmodified, in source code or in binary form.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met: redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer;
+ * redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution;
+ * neither the name of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "dev/arm/ssc.hh"
+
+namespace gem5
+{
+
+SysSecCtrl::SysSecCtrl(const Params &p)
+  : BasicPioDevice(p, 0x1000),
+    sscDbgcfgStat("ssc_dbgcfg_stat", p.ssc_dbgcfg_stat),
+    sscDbgcfgSet("ssc_dbgcfg_set"),
+    sscDbgcfgClr("ssc_dbgcfg_clr"),
+    space0("space0", 0x28 - 0x1c),
+    sscAuxDbgcfg("ssc_aux_dbgcfg"),
+    space1("space1", 0x4),
+    sscAuxGpretn("ssc_aux_gpretn"),
+    space2("space2", 0x40 - 0x34),
+    sscVersion("ssc_version", p.ssc_version),
+    space3("space3", 0x100 - 0x44),
+    sscSwScratch("ssc_sw_scratch"),
+    space4("space4", 0x200 - 0x180),
+    sscSwCap("ssc_sw_cap"),
+    sscSwCapCtrl("ssc_sw_capctrl"),
+    space5("space5", 0x500 - 0x304),
+    sscChipIdSt("ssc_chipid_st"),
+    space6("space6", 0xfd0 - 0x504),
+    sscPid4("ssc_pid4", p.ssc_pid4),
+    space7("space7", 0xfe0 - 0xfd4),
+    sscPid0("ssc_pid0", p.ssc_pid0),
+    sscPid1("ssc_pid1", p.ssc_pid1),
+    sscPid2("ssc_pid2", p.ssc_pid2),
+    space8("space8", 0xff0 - 0xfec),
+    compid0("compid0", p.compid0),
+    compid1("compid1", p.compid1),
+    compid2("compid2", p.compid2),
+    compid3("compid3", p.compid3),
+    regBank("ssc", 0x0010)
+{
+    // RO registers
+    sscDbgcfgStat.readonly();
+    sscVersion.readonly();
+    sscChipIdSt.readonly();
+    sscPid0.readonly();
+    sscPid1.readonly();
+    sscPid2.readonly();
+    sscPid4.readonly();
+    compid0.readonly();
+    compid1.readonly();
+    compid2.readonly();
+    compid3.readonly();
+
+    regBank.addRegisters({
+        sscDbgcfgStat, sscDbgcfgSet, sscDbgcfgClr,
+        space0,
+        sscAuxDbgcfg,
+        space1,
+        sscAuxGpretn,
+        space2,
+        sscVersion,
+        space3,
+        sscSwScratch,
+        space4,
+        sscSwCap, sscSwCapCtrl,
+        space5,
+        sscChipIdSt,
+        space6,
+        sscPid4,
+        space7,
+        sscPid0, sscPid1, sscPid2,
+        space8,
+        compid0, compid1, compid2, compid3,
+    });
+}
+
+Tick
+SysSecCtrl::read(PacketPtr pkt)
+{
+    assert(pkt->getAddr() >= pioAddr && pkt->getAddr() < pioAddr + pioSize);
+    Addr daddr = pkt->getAddr() - pioAddr;
+
+    regBank.read(daddr, pkt->getPtr<void>(), pkt->getSize());
+
+    pkt->makeAtomicResponse();
+    return pioDelay;
+}
+
+Tick
+SysSecCtrl::write(PacketPtr pkt)
+{
+    assert(pkt->getAddr() >= pioAddr && pkt->getAddr() < pioAddr + pioSize);
+    Addr daddr = pkt->getAddr() - pioAddr;
+
+    regBank.write(daddr, pkt->getPtr<void>(), pkt->getSize());
+
+    pkt->makeAtomicResponse();
+    return pioDelay;
+}
+
+}
diff --git a/src/dev/arm/ssc.hh b/src/dev/arm/ssc.hh
new file mode 100644
index 0000000..25475d9
--- /dev/null
+++ b/src/dev/arm/ssc.hh
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2022 Arm Limited
+ * All rights reserved
+ *
+ * The license below extends only to copyright in the software and shall
+ * not be construed as granting a license to any other intellectual
+ * property including but not limited to intellectual property relating
+ * to a hardware implementation of the functionality of the software
+ * licensed hereunder.  You may use the software subject to the license
+ * terms below provided that you ensure that this notice is replicated
+ * unmodified and in its entirety in all distributions of the software,
+ * modified or unmodified, in source code or in binary form.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met: redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer;
+ * redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution;
+ * neither the name of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __DEV_ARM_SSC_H__
+#define __DEV_ARM_SSC_H__
+
+#include "dev/io_device.hh"
+#include "dev/reg_bank.hh"
+#include "params/SysSecCtrl.hh"
+
+namespace gem5
+{
+
+/** System Security Control registers */
+class SysSecCtrl : public BasicPioDevice
+{
+  public:
+    PARAMS(SysSecCtrl);
+    SysSecCtrl(const Params &p);
+
+    /**
+     * Handle a read to the device
+     * @param pkt The memory request.
+     * @param data Where to put the data.
+     */
+    Tick read(PacketPtr pkt) override;
+
+    /**
+     * All writes are simply ignored.
+     * @param pkt The memory request.
+     * @param data the data
+     */
+    Tick write(PacketPtr pkt) override;
+
+  protected:
+    using Register = RegisterBankLE::Register32LE;
+    using Space = RegisterBankLE::RegisterRaz;
+    template <size_t Size>
+    using Block = RegisterBankLE::RegisterLBuf<Size>;
+
+    Register sscDbgcfgStat;
+    Register sscDbgcfgSet;
+    Register sscDbgcfgClr;
+    Space space0;
+    Register sscAuxDbgcfg;
+    Space space1;
+    Register sscAuxGpretn;
+    Space space2;
+    Register sscVersion;
+    Space space3;
+    Block<0x80> sscSwScratch;
+    Space space4;
+    Block<0x100> sscSwCap;
+    Register sscSwCapCtrl;
+    Space space5;
+    Register sscChipIdSt;
+    Space space6;
+    Register sscPid4;
+    Space space7;
+    Register sscPid0;
+    Register sscPid1;
+    Register sscPid2;
+    Space space8;
+    Register compid0;
+    Register compid1;
+    Register compid2;
+    Register compid3;
+
+    RegisterBankLE regBank;
+};
+
+} // namespace gem5
+
+#endif