summaryrefslogtreecommitdiff
path: root/tools
diff options
context:
space:
mode:
authorEmanuele Ghidoli <emanuele.ghidoli@toradex.com>2023-12-01 14:36:20 +0100
committerEmanuele Ghidoli <emanuele.ghidoli@toradex.com>2023-12-01 14:36:20 +0100
commitff20984bc78933c081ab8f22a84dde8cdb38e8b9 (patch)
treec626e16fdb2e6d51a7dbc27bad5a556a8549ea4a /tools
parent536d0d5eef241a80a352704d82f2284faac2b046 (diff)
parent71b8c840ca61a4e11b2cdf63b0e6580ecb427912 (diff)
Merge tag '09.01.00.006' into toradex_ti-09.01.00.006
RC Release 09.01.00.006
Diffstat (limited to 'tools')
-rw-r--r--tools/binman/btool/openssl.py22
-rw-r--r--tools/binman/entries.rst1
-rw-r--r--tools/binman/etype/ti_secure.py90
-rw-r--r--tools/binman/etype/ti_secure_rom.py16
-rw-r--r--tools/binman/etype/x509_cert.py6
-rw-r--r--tools/binman/ftest.py22
-rw-r--r--tools/binman/test/280_ti_secure_rom.dts1
-rw-r--r--tools/binman/test/319_ti_secure_firewall.dts28
-rw-r--r--tools/binman/test/320_ti_secure_firewall_missing_property.dts28
-rw-r--r--tools/fdtgrep.c8
10 files changed, 209 insertions, 13 deletions
diff --git a/tools/binman/btool/openssl.py b/tools/binman/btool/openssl.py
index aad3b61ae2..ac1eaf5ded 100644
--- a/tools/binman/btool/openssl.py
+++ b/tools/binman/btool/openssl.py
@@ -82,7 +82,7 @@ imageSize = INTEGER:{len(indata)}
return self.run_cmd(*args)
def x509_cert_sysfw(self, cert_fname, input_fname, key_fname, sw_rev,
- config_fname, req_dist_name_dict):
+ config_fname, req_dist_name_dict, firewall_cert_data):
"""Create a certificate to be booted by system firmware
Args:
@@ -94,6 +94,13 @@ imageSize = INTEGER:{len(indata)}
req_dist_name_dict (dict): Dictionary containing key-value pairs of
req_distinguished_name section extensions, must contain extensions for
C, ST, L, O, OU, CN and emailAddress
+ firewall_cert_data (dict):
+ - auth_in_place (int): The Priv ID for copying as the
+ specific host in firewall protected region
+ - num_firewalls (int): The number of firewalls in the
+ extended certificate
+ - certificate (str): Extended firewall certificate with
+ the information for the firewall configurations.
Returns:
str: Tool output
@@ -121,6 +128,7 @@ basicConstraints = CA:true
1.3.6.1.4.1.294.1.3 = ASN1:SEQUENCE:swrv
1.3.6.1.4.1.294.1.34 = ASN1:SEQUENCE:sysfw_image_integrity
1.3.6.1.4.1.294.1.35 = ASN1:SEQUENCE:sysfw_image_load
+1.3.6.1.4.1.294.1.37 = ASN1:SEQUENCE:firewall
[ swrv ]
swrv = INTEGER:{sw_rev}
@@ -132,7 +140,11 @@ imageSize = INTEGER:{len(indata)}
[ sysfw_image_load ]
destAddr = FORMAT:HEX,OCT:00000000
-authInPlace = INTEGER:2
+authInPlace = INTEGER:{hex(firewall_cert_data['auth_in_place'])}
+
+[ firewall ]
+numFirewallRegions = INTEGER:{firewall_cert_data['num_firewalls']}
+{firewall_cert_data['certificate']}
''', file=outf)
args = ['req', '-new', '-x509', '-key', key_fname, '-nodes',
'-outform', 'DER', '-out', cert_fname, '-config', config_fname,
@@ -155,6 +167,7 @@ authInPlace = INTEGER:2
C, ST, L, O, OU, CN and emailAddress
cert_type (int): Certification type
bootcore (int): Booting core
+ bootcore_opts(int): Booting core option (split/lockstep mode)
load_addr (int): Load address of image
sha (int): Hash function
@@ -225,7 +238,7 @@ emailAddress = {req_dist_name_dict['emailAddress']}
imagesize_sbl, hashval_sbl, load_addr_sysfw, imagesize_sysfw,
hashval_sysfw, load_addr_sysfw_data, imagesize_sysfw_data,
hashval_sysfw_data, sysfw_inner_cert_ext_boot_block,
- dm_data_ext_boot_block):
+ dm_data_ext_boot_block, bootcore_opts):
"""Create a certificate
Args:
@@ -241,6 +254,7 @@ emailAddress = {req_dist_name_dict['emailAddress']}
bootcore (int): Booting core
load_addr (int): Load address of image
sha (int): Hash function
+ bootcore_opts (int): Boot core option (split/lockstep mode)
Returns:
str: Tool output
@@ -285,7 +299,7 @@ sysfw_data=SEQUENCE:sysfw_data
[sbl]
compType = INTEGER:1
bootCore = INTEGER:16
-compOpts = INTEGER:0
+compOpts = INTEGER:{bootcore_opts}
destAddr = FORMAT:HEX,OCT:{load_addr:08x}
compSize = INTEGER:{imagesize_sbl}
shaType = OID:{sha_type}
diff --git a/tools/binman/entries.rst b/tools/binman/entries.rst
index f9900fe6be..fa6d1b6afa 100644
--- a/tools/binman/entries.rst
+++ b/tools/binman/entries.rst
@@ -1739,6 +1739,7 @@ Properties / Entry arguments:
- core: core on which bootloader runs, valid cores are 'secure' and 'public'
- content: phandle of SPL in case of legacy bootflow or phandles of component binaries
in case of combined bootflow
+ - core-opts (optional): split-mode (0) or lockstep mode (1) set to 0 by default
The following properties are only for generating a combined bootflow binary:
- sysfw-inner-cert: boolean if binary contains sysfw inner certificate
diff --git a/tools/binman/etype/ti_secure.py b/tools/binman/etype/ti_secure.py
index b1f5d89198..f80eb542c9 100644
--- a/tools/binman/etype/ti_secure.py
+++ b/tools/binman/etype/ti_secure.py
@@ -7,9 +7,40 @@
from binman.entry import EntryArg
from binman.etype.x509_cert import Entry_x509_cert
+from dataclasses import dataclass
from dtoc import fdt_util
+@dataclass
+class Firewall():
+ id: int
+ region: int
+ control : int
+ permissions: list[hex]
+ start_address: str
+ end_address: str
+
+ def __post_init__(self):
+ for key, val in self.__dict__.items():
+ if val is None:
+ raise Exception(f"{key} can't be None in firewall node")
+
+ def get_certificate(self) -> str:
+ unique_identifier = f"{self.id}{self.region}"
+ cert = f"""
+firewallID{unique_identifier} = INTEGER:{self.id}
+region{unique_identifier} = INTEGER:{self.region}
+control{unique_identifier} = INTEGER:{hex(self.control)}
+nPermissionRegs{unique_identifier} = INTEGER:{len(self.permissions)}
+"""
+ for index, permission in enumerate(self.permissions):
+ cert += f"""permissions{unique_identifier}{index} = INTEGER:{hex(permission)}
+"""
+ cert += f"""startAddress{unique_identifier} = FORMAT:HEX,OCT:{self.start_address:02x}
+endAddress{unique_identifier} = FORMAT:HEX,OCT:{self.end_address:02x}
+"""
+ return cert
+
class Entry_ti_secure(Entry_x509_cert):
"""Entry containing a TI x509 certificate binary
@@ -17,6 +48,11 @@ class Entry_ti_secure(Entry_x509_cert):
- content: List of phandles to entries to sign
- keyfile: Filename of file containing key to sign binary with
- sha: Hash function to be used for signing
+ - auth-in-place: This is an integer field that contains two pieces
+ of information
+ Lower Byte - Remains 0x02 as per our use case
+ ( 0x02: Move the authenticated binary back to the header )
+ Upper Byte - The Host ID of the core owning the firewall
Output files:
- input.<unique_name> - input file passed to openssl
@@ -25,6 +61,35 @@ class Entry_ti_secure(Entry_x509_cert):
- cert.<unique_name> - output file generated by openssl (which is
used as the entry contents)
+ Depending on auth-in-place information in the inputs, we read the
+ firewall nodes that describe the configurations of firewall that TIFS
+ will be doing after reading the certificate.
+
+ The syntax of the firewall nodes are as such:
+
+ firewall-257-0 {
+ id = <257>; /* The ID of the firewall being configured */
+ region = <0>; /* Region number to configure */
+
+ control = /* The control register */
+ <(FWCTRL_EN | FWCTRL_LOCK | FWCTRL_BG | FWCTRL_CACHE)>;
+
+ permissions = /* The permission registers */
+ <((FWPRIVID_ALL << FWPRIVID_SHIFT) |
+ FWPERM_SECURE_PRIV_RWCD |
+ FWPERM_SECURE_USER_RWCD |
+ FWPERM_NON_SECURE_PRIV_RWCD |
+ FWPERM_NON_SECURE_USER_RWCD)>;
+
+ /* More defines can be found in k3-security.h */
+
+ start_address = /* The Start Address of the firewall */
+ <0x0 0x0>;
+ end_address = /* The End Address of the firewall */
+ <0xff 0xffffffff>;
+ };
+
+
openssl signs the provided data, using the TI templated config file and
writes the signature in this entry. This allows verification that the
data is genuine.
@@ -32,11 +97,20 @@ class Entry_ti_secure(Entry_x509_cert):
def __init__(self, section, etype, node):
super().__init__(section, etype, node)
self.openssl = None
+ self.firewall_cert_data: dict = {
+ 'auth_in_place': 0x02,
+ 'num_firewalls': 0,
+ 'certificate': '',
+ }
def ReadNode(self):
super().ReadNode()
self.key_fname = self.GetEntryArgsOrProps([
EntryArg('keyfile', str)], required=True)[0]
+ auth_in_place = fdt_util.GetInt(self._node, 'auth-in-place')
+ if auth_in_place:
+ self.firewall_cert_data['auth_in_place'] = auth_in_place
+ self.ReadFirewallNode()
self.sha = fdt_util.GetInt(self._node, 'sha', 512)
self.req_dist_name = {'C': 'US',
'ST': 'TX',
@@ -46,6 +120,22 @@ class Entry_ti_secure(Entry_x509_cert):
'CN': 'TI Support',
'emailAddress': 'support@ti.com'}
+ def ReadFirewallNode(self):
+ self.firewall_cert_data['certificate'] = ""
+ self.firewall_cert_data['num_firewalls'] = 0
+ for node in self._node.subnodes:
+ if 'firewall' in node.name:
+ firewall = Firewall(
+ fdt_util.GetInt(node, 'id'),
+ fdt_util.GetInt(node, 'region'),
+ fdt_util.GetInt(node, 'control'),
+ fdt_util.GetPhandleList(node, 'permissions'),
+ fdt_util.GetInt64(node, 'start_address'),
+ fdt_util.GetInt64(node, 'end_address'),
+ )
+ self.firewall_cert_data['num_firewalls'] += 1
+ self.firewall_cert_data['certificate'] += firewall.get_certificate()
+
def GetCertificate(self, required):
"""Get the contents of this entry
diff --git a/tools/binman/etype/ti_secure_rom.py b/tools/binman/etype/ti_secure_rom.py
index da03c90ef1..ff55d9d1a4 100644
--- a/tools/binman/etype/ti_secure_rom.py
+++ b/tools/binman/etype/ti_secure_rom.py
@@ -32,6 +32,7 @@ class Entry_ti_secure_rom(Entry_x509_cert):
- core: core on which bootloader runs, valid cores are 'secure' and 'public'
- content: phandle of SPL in case of legacy bootflow or phandles of component binaries
in case of combined bootflow
+ - core-opts (optional): split-mode (0) or lockstep mode (1) set to 0 by default
The following properties are only for generating a combined bootflow binary:
- sysfw-inner-cert: boolean if binary contains sysfw inner certificate
@@ -70,6 +71,7 @@ class Entry_ti_secure_rom(Entry_x509_cert):
self.sw_rev = fdt_util.GetInt(self._node, 'sw-rev', 1)
self.sha = fdt_util.GetInt(self._node, 'sha', 512)
self.core = fdt_util.GetString(self._node, 'core', 'secure')
+ self.bootcore_opts = fdt_util.GetInt(self._node, 'core-opts')
self.key_fname = self.GetEntryArgsOrProps([
EntryArg('keyfile', str)], required=True)[0]
if self.combined:
@@ -98,22 +100,19 @@ class Entry_ti_secure_rom(Entry_x509_cert):
bytes content of the entry, which is the certificate binary for the
provided data
"""
+ if self.bootcore_opts is None:
+ self.bootcore_opts = 0
+
if self.core == 'secure':
if self.countersign:
self.cert_type = 3
else:
self.cert_type = 2
-
- if self.fsstub:
- self.bootcore_opts = 0
- else:
- self.bootcore_opts = 32
-
self.bootcore = 0
else:
self.cert_type = 1
self.bootcore = 16
- self.bootcore_opts = 0
+
return super().GetCertificate(required=required, type='rom')
def CombinedGetCertificate(self, required):
@@ -132,6 +131,9 @@ class Entry_ti_secure_rom(Entry_x509_cert):
self.num_comps = 3
self.sha_type = SHA_OIDS[self.sha]
+ if self.bootcore_opts is None:
+ self.bootcore_opts = 0
+
# sbl
self.content = fdt_util.GetPhandleList(self._node, 'content-sbl')
input_data_sbl = self.GetContents(required)
diff --git a/tools/binman/etype/x509_cert.py b/tools/binman/etype/x509_cert.py
index d028cfe38c..cd240559e5 100644
--- a/tools/binman/etype/x509_cert.py
+++ b/tools/binman/etype/x509_cert.py
@@ -98,7 +98,8 @@ class Entry_x509_cert(Entry_collection):
key_fname=self.key_fname,
config_fname=config_fname,
sw_rev=self.sw_rev,
- req_dist_name_dict=self.req_dist_name)
+ req_dist_name_dict=self.req_dist_name,
+ firewall_cert_data=self.firewall_cert_data)
elif type == 'rom':
stdout = self.openssl.x509_cert_rom(
cert_fname=output_fname,
@@ -136,7 +137,8 @@ class Entry_x509_cert(Entry_collection):
imagesize_sysfw_data=self.imagesize_sysfw_data,
hashval_sysfw_data=self.hashval_sysfw_data,
sysfw_inner_cert_ext_boot_block=self.sysfw_inner_cert_ext_boot_block,
- dm_data_ext_boot_block=self.dm_data_ext_boot_block
+ dm_data_ext_boot_block=self.dm_data_ext_boot_block,
+ bootcore_opts=self.bootcore_opts
)
if stdout is not None:
data = tools.read_file(output_fname)
diff --git a/tools/binman/ftest.py b/tools/binman/ftest.py
index 1555ce9898..5a5da4f53d 100644
--- a/tools/binman/ftest.py
+++ b/tools/binman/ftest.py
@@ -6463,6 +6463,28 @@ fdt fdtmap Extract the devicetree blob from the fdtmap
entry_args=entry_args)[0]
self.assertGreater(len(data), len(TI_UNSECURE_DATA))
+ def testPackTiSecureFirewall(self):
+ """Test that an image with a TI secured binary can be created"""
+ keyfile = self.TestFile('key.key')
+ entry_args = {
+ 'keyfile': keyfile,
+ }
+ data_no_firewall = self._DoReadFileDtb('296_ti_secure.dts',
+ entry_args=entry_args)[0]
+ data_firewall = self._DoReadFileDtb('319_ti_secure_firewall.dts',
+ entry_args=entry_args)[0]
+ self.assertGreater(len(data_firewall),len(data_no_firewall))
+
+ def testPackTiSecureFirewallMissingProperty(self):
+ """Test that an image with a TI secured binary can be created"""
+ keyfile = self.TestFile('key.key')
+ entry_args = {
+ 'keyfile': keyfile,
+ }
+ data_firewall = self._DoReadFileDtb('320_ti_secure_firewall_missing_property.dts',
+ entry_args=entry_args)[0]
+ self.assertRegex("can't be None in firewall node", str(e.exception))
+
def testPackTiSecureMissingTool(self):
"""Test that an image with a TI secured binary (non-functional) can be created
when openssl is missing"""
diff --git a/tools/binman/test/280_ti_secure_rom.dts b/tools/binman/test/280_ti_secure_rom.dts
index d1313769f4..1a3eca9425 100644
--- a/tools/binman/test/280_ti_secure_rom.dts
+++ b/tools/binman/test/280_ti_secure_rom.dts
@@ -9,6 +9,7 @@
binman {
ti-secure-rom {
content = <&unsecure_binary>;
+ core-opts = <2>;
};
unsecure_binary: blob-ext {
filename = "ti_unsecure.bin";
diff --git a/tools/binman/test/319_ti_secure_firewall.dts b/tools/binman/test/319_ti_secure_firewall.dts
new file mode 100644
index 0000000000..7ec407fa67
--- /dev/null
+++ b/tools/binman/test/319_ti_secure_firewall.dts
@@ -0,0 +1,28 @@
+// SPDX-License-Identifier: GPL-2.0+
+
+/dts-v1/;
+
+/ {
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ binman {
+ ti-secure {
+ content = <&unsecure_binary>;
+ auth-in-place = <0xa02>;
+
+ firewall-0-2 {
+ id = <0>;
+ region = <2>;
+ control = <0x31a>;
+ permissions = <0xc3ffff>;
+ start_address = <0x0 0x9e800000>;
+ end_address = <0x0 0x9fffffff>;
+ };
+
+ };
+ unsecure_binary: blob-ext {
+ filename = "ti_unsecure.bin";
+ };
+ };
+};
diff --git a/tools/binman/test/320_ti_secure_firewall_missing_property.dts b/tools/binman/test/320_ti_secure_firewall_missing_property.dts
new file mode 100644
index 0000000000..8e995ffa47
--- /dev/null
+++ b/tools/binman/test/320_ti_secure_firewall_missing_property.dts
@@ -0,0 +1,28 @@
+// SPDX-License-Identifier: GPL-2.0+
+
+/dts-v1/;
+
+/ {
+ #address-cells = <1>;
+ #size-cells = <1>;
+
+ binman {
+ ti-secure {
+ content = <&unsecure_binary>;
+ auth-in-place = <0xa02>;
+
+ firewall-0-2 {
+ // id = <0>;
+ region = <2>;
+ control = <0x31a>;
+ permissions = <0xc3ffff>;
+ start_address = <0x0 0x9e800000>;
+ end_address = <0x0 0x9fffffff>;
+ };
+
+ };
+ unsecure_binary: blob-ext {
+ filename = "ti_unsecure.bin";
+ };
+ };
+};
diff --git a/tools/fdtgrep.c b/tools/fdtgrep.c
index 7eabcab439..706b4a35f4 100644
--- a/tools/fdtgrep.c
+++ b/tools/fdtgrep.c
@@ -22,6 +22,8 @@
#include "fdt_host.h"
#include "libfdt_internal.h"
+#include <linux/kconfig.h>
+
/* Define DEBUG to get some debugging output on stderr */
#ifdef DEBUG
#define debug(a, b...) fprintf(stderr, a, ## b)
@@ -1234,6 +1236,12 @@ int main(int argc, char *argv[])
disp.fout = stdout;
}
+ if (IS_ENABLED(CONFIG_SPL_LOAD_FIT_APPLY_OVERLAY)) {
+ /* include symbol table */
+ if (value_add(&disp, &disp.value_head, FDT_IS_NODE, 1, "/__symbols__"))
+ usage("Cannot add __symbols__ value");
+ }
+
/* Run the grep and output the results */
ret = do_fdtgrep(&disp, filename);
if (disp.output_fname)