Skip to content

Commit ab42e1f

Browse files
luoji-nxp“nxf90552”
authored and
“nxf90552”
committed
Add device attestation based on ELE
Support device attestation based on EdgeLock Enclave(ELE). Attestation certifications and keys should be provisioned into device in advance. The official tool to provide signed content is not ready, so we disable the device attestation feature based on ELE first. It's currently only supported by i.MX 93 platform. Change-Id: I39c79efa17a99266113e2bf28204d0c23b81af1d Signed-off-by: Ji Luo <ji.luo@nxp.com> Reviewed-on: http://androidsource.nxp.com/project/23345 Reviewed-by: Elven Wang <elven.wang@nxp.com>
1 parent e385c0f commit ab42e1f

7 files changed

+287
-12
lines changed

examples/platform/linux/AppMain.cpp

+7-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
/*
22
*
33
* Copyright (c) 2021-2022 Project CHIP Authors
4+
* Copyright 2023, 2025 NXP
45
* All rights reserved.
56
*
67
* Licensed under the Apache License, Version 2.0 (the "License");
@@ -127,8 +128,11 @@
127128
#endif // CHIP_DEVICE_LAYER_TARGET_LINUX
128129

129130
#if CHIP_ATTESTATION_TRUSTY_OS
130-
#include "DeviceAttestationCreds.h"
131+
#include "DeviceAttestationCredsTrusty.h"
131132
using namespace chip::Credentials::Trusty;
133+
#elif CHIP_ATTESTATION_ELE
134+
#include "DeviceAttestationCredsEle.h"
135+
using namespace chip::Credentials::ele;
132136
#endif
133137

134138
#if CHIP_OP_KEYSTORE_TRUSTY_OS
@@ -737,6 +741,8 @@ void ChipLinuxAppMainLoop(AppMainLoopImplementation * impl)
737741
// Initialize device attestation config
738742
#if CHIP_ATTESTATION_TRUSTY_OS
739743
SetDeviceAttestationCredentialsProvider(&TrustyDACProvider::GetTrustyDACProvider());
744+
#elif CHIP_ATTESTATION_ELE
745+
SetDeviceAttestationCredentialsProvider(&EleDACProvider::GetEleDACProvider());
740746
#else
741747
SetDeviceAttestationCredentialsProvider(LinuxDeviceOptions::GetInstance().dacProvider);
742748
#endif

examples/platform/linux/BUILD.gn

+9-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
# Copyright (c) 2020 Project CHIP Authors
2+
# Copyright 2025 NXP
23
#
34
# Licensed under the Apache License, Version 2.0 (the "License");
45
# you may not use this file except in compliance with the License.
@@ -100,15 +101,18 @@ source_set("app-main") {
100101

101102
if (chip_with_trusty_os == 1) {
102103
sources += [
103-
"DeviceAttestationCreds.cpp",
104-
"DeviceAttestationCreds.h",
104+
"DeviceAttestationCredsTrusty.cpp",
105+
"DeviceAttestationCredsTrusty.h",
105106
"PersistentStorageOperationalKeystoreTrusty.cpp",
106107
"PersistentStorageOperationalKeystoreTrusty.h",
107108
]
108109
}
109110

110111
if (chip_with_imx_ele == 1) {
111112
sources += [
113+
#TODO enable this when official tool ready
114+
# "DeviceAttestationCredsEle.cpp",
115+
# "DeviceAttestationCredsEle.h",
112116
"PersistentStorageOperationalKeystoreEle.cpp",
113117
"PersistentStorageOperationalKeystoreEle.h",
114118
]
@@ -163,8 +167,11 @@ source_set("app-main") {
163167

164168
if (chip_with_imx_ele == 1) {
165169
defines += [ "CHIP_OP_KEYSTORE_ELE=1" ]
170+
#TODO enable this when official tool ready
171+
# defines += [ "CHIP_ATTESTATION_ELE=1" ]
166172
} else {
167173
defines += [ "CHIP_OP_KEYSTORE_ELE=0" ]
174+
defines += [ "CHIP_ATTESTATION_ELE=0" ]
168175
}
169176

170177
if (chip_enable_pw_rpc) {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,219 @@
1+
/*
2+
*
3+
* Copyright (c) 2021-2022 Project CHIP Authors
4+
* Copyright 2023, 2025 NXP
5+
*
6+
* Licensed under the Apache License, Version 2.0 (the "License");
7+
* you may not use this file except in compliance with the License.
8+
* You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing, software
13+
* distributed under the License is distributed on an "AS IS" BASIS,
14+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
* See the License for the specific language governing permissions and
16+
* limitations under the License.
17+
*
18+
*/
19+
#include "DeviceAttestationCredsEle.h"
20+
21+
#include <crypto/CHIPCryptoPAL.h>
22+
#include <lib/core/CHIPError.h>
23+
#include <lib/support/Span.h>
24+
25+
#define KEY_STORE_ID (0xBBBB)
26+
#define AUTHEN_NONCE (0x2222)
27+
#define PAI_DATA_ID 0x1111
28+
#define DAC_DATA_ID 0x1112
29+
#define CD_DATA_ID 0x1113
30+
#define DAC_PRIVATE_KEY_ID 0x1114
31+
32+
namespace chip {
33+
namespace Credentials {
34+
namespace ele {
35+
36+
EleDACProvider::EleDACProvider()
37+
{
38+
hsm_err_t err;
39+
40+
// open the session
41+
open_session_args_t open_session_args = { 0 };
42+
open_session_args.mu_type = HSM1;
43+
err = hsm_open_session(&open_session_args, &hsm_session_hdl);
44+
if (err != HSM_NO_ERROR)
45+
{
46+
ChipLogDetail(Crypto, "ELE device attestation session open failed. ret: 0x%x\n", err);
47+
return;
48+
}
49+
else
50+
{
51+
ChipLogDetail(Crypto, "ELE device attestation session open successfully.\n");
52+
}
53+
54+
// open the keystore
55+
open_svc_key_store_args_t open_svc_key_store_args = { 0 };
56+
open_svc_key_store_args.key_store_identifier = KEY_STORE_ID;
57+
open_svc_key_store_args.authentication_nonce = AUTHEN_NONCE;
58+
// try to create a new keystore, if it already exist, open it
59+
open_svc_key_store_args.flags = (HSM_SVC_KEY_STORE_FLAGS_CREATE | HSM_SVC_KEY_STORE_FLAGS_STRICT_OPERATION);
60+
err = hsm_open_key_store_service(hsm_session_hdl, &open_svc_key_store_args, &key_store_hdl);
61+
if (err == HSM_KEY_STORE_CONFLICT)
62+
{
63+
ChipLogDetail(Crypto, "device attestation keystore already existed, open it...\n");
64+
open_svc_key_store_args.flags = HSM_SVC_KEY_STORE_FLAGS_LOAD;
65+
err = hsm_open_key_store_service(hsm_session_hdl, &open_svc_key_store_args, &key_store_hdl);
66+
if (err != HSM_NO_ERROR)
67+
{
68+
ChipLogDetail(Crypto, "device attestation keystore open failed. ret:0x%x\n", err);
69+
return;
70+
}
71+
else
72+
ChipLogDetail(Crypto, "device attestation keystore open successfully.\n");
73+
}
74+
else
75+
{
76+
ChipLogDetail(Crypto, "device attestation keystore created successfully.\n");
77+
}
78+
}
79+
80+
EleDACProvider::~EleDACProvider()
81+
{
82+
hsm_err_t err;
83+
84+
ChipLogDetail(Crypto, "close all ELE device attestation services.\n");
85+
86+
err = hsm_close_key_store_service(key_store_hdl);
87+
key_store_hdl = 0;
88+
ChipLogDetail(Crypto, "close device attestation key store service returns:0x%x\n", err);
89+
90+
err = hsm_close_session(hsm_session_hdl);
91+
hsm_session_hdl = 0;
92+
ChipLogDetail(Crypto, "close ELE device attestation session returns:0x%x\n", err);
93+
}
94+
95+
CHIP_ERROR EleDACProvider::GetDeviceAttestationCert(MutableByteSpan & out_dac_buffer)
96+
{
97+
op_data_storage_args_t data_storage_args;
98+
hsm_err_t err;
99+
100+
data_storage_args.svc_flags = 0;
101+
data_storage_args.data = out_dac_buffer.data();
102+
data_storage_args.data_size = out_dac_buffer.size();
103+
data_storage_args.data_id = DAC_DATA_ID;
104+
data_storage_args.flags |= HSM_OP_DATA_STORAGE_FLAGS_RETRIEVE;
105+
err = hsm_data_ops(key_store_hdl, &data_storage_args);
106+
if (err)
107+
{
108+
ChipLogDetail(Crypto, "ELE get DAC failed. ret: 0x%x\n", err);
109+
return CHIP_ERROR_CERT_LOAD_FAILED;
110+
}
111+
112+
out_dac_buffer.reduce_size(data_storage_args.exp_output_size);
113+
return CHIP_NO_ERROR;
114+
}
115+
116+
CHIP_ERROR EleDACProvider::GetProductAttestationIntermediateCert(MutableByteSpan & out_pai_buffer)
117+
{
118+
op_data_storage_args_t data_storage_args;
119+
hsm_err_t err;
120+
121+
data_storage_args.svc_flags = 0;
122+
data_storage_args.data = out_pai_buffer.data();
123+
data_storage_args.data_size = out_pai_buffer.size();
124+
data_storage_args.data_id = PAI_DATA_ID;
125+
data_storage_args.flags |= HSM_OP_DATA_STORAGE_FLAGS_RETRIEVE;
126+
err = hsm_data_ops(key_store_hdl, &data_storage_args);
127+
if (err)
128+
{
129+
ChipLogDetail(Crypto, "ELE get PAI failed. ret: 0x%x\n", err);
130+
return CHIP_ERROR_CERT_LOAD_FAILED;
131+
}
132+
133+
out_pai_buffer.reduce_size(data_storage_args.exp_output_size);
134+
return CHIP_NO_ERROR;
135+
}
136+
137+
CHIP_ERROR EleDACProvider::GetCertificationDeclaration(MutableByteSpan & out_cd_buffer)
138+
{
139+
op_data_storage_args_t data_storage_args;
140+
hsm_err_t err;
141+
142+
data_storage_args.svc_flags = 0;
143+
data_storage_args.data = out_cd_buffer.data();
144+
data_storage_args.data_size = out_cd_buffer.size();
145+
data_storage_args.data_id = CD_DATA_ID;
146+
data_storage_args.flags |= HSM_OP_DATA_STORAGE_FLAGS_RETRIEVE;
147+
err = hsm_data_ops(key_store_hdl, &data_storage_args);
148+
if (err)
149+
{
150+
ChipLogDetail(Crypto, "ELE get CD failed. ret: 0x%x\n", err);
151+
return CHIP_ERROR_CERT_LOAD_FAILED;
152+
}
153+
154+
out_cd_buffer.reduce_size(data_storage_args.exp_output_size);
155+
return CHIP_NO_ERROR;
156+
}
157+
158+
CHIP_ERROR EleDACProvider::GetFirmwareInformation(MutableByteSpan & out_firmware_info_buffer)
159+
{
160+
// TODO: We need a real example FirmwareInformation to be populated.
161+
out_firmware_info_buffer.reduce_size(0);
162+
163+
return CHIP_NO_ERROR;
164+
}
165+
166+
CHIP_ERROR EleDACProvider::SignWithDeviceAttestationKey(const ByteSpan & message_to_sign, MutableByteSpan & out_signature_buffer)
167+
{
168+
open_svc_sign_gen_args_t open_sig_gen_args;
169+
op_generate_sign_args_t sig_gen_args;
170+
uint8_t signature[64];
171+
hsm_hdl_t sig_gen_hdl;
172+
size_t out_size = 0;
173+
hsm_err_t hsmret;
174+
175+
VerifyOrReturnError(IsSpanUsable(out_signature_buffer), CHIP_ERROR_INVALID_ARGUMENT);
176+
VerifyOrReturnError(IsSpanUsable(message_to_sign), CHIP_ERROR_INVALID_ARGUMENT);
177+
VerifyOrReturnError(out_signature_buffer.size() >= sizeof(signature), CHIP_ERROR_BUFFER_TOO_SMALL);
178+
179+
// open signature generation service
180+
memset(&open_sig_gen_args, 0, sizeof(open_sig_gen_args));
181+
hsmret = hsm_open_signature_generation_service(key_store_hdl, &open_sig_gen_args, &sig_gen_hdl);
182+
if (hsmret != HSM_NO_ERROR)
183+
{
184+
ChipLogDetail(Crypto, "open signature generation service failed. ret:0x%x\n", hsmret);
185+
return CHIP_ERROR_HSM;
186+
}
187+
188+
// generate signature
189+
memset(&sig_gen_args, 0, sizeof(sig_gen_args));
190+
sig_gen_args.key_identifier = DAC_PRIVATE_KEY_ID;
191+
sig_gen_args.scheme_id = HSM_SIGNATURE_SCHEME_ECDSA_SHA256;
192+
sig_gen_args.message = (uint8_t *) (message_to_sign.data());
193+
sig_gen_args.signature = signature;
194+
sig_gen_args.message_size = message_to_sign.size();
195+
sig_gen_args.signature_size = sizeof(signature);
196+
sig_gen_args.flags = HSM_OP_GENERATE_SIGN_FLAGS_INPUT_MESSAGE;
197+
hsmret = hsm_generate_signature(sig_gen_hdl, &sig_gen_args);
198+
hsm_close_signature_generation_service(sig_gen_hdl);
199+
if (hsmret != HSM_NO_ERROR)
200+
{
201+
ChipLogDetail(Crypto, "generate signature failed. ret:0x%x\n", hsmret);
202+
return CHIP_ERROR_HSM;
203+
}
204+
205+
memcpy(out_signature_buffer.data(), signature, sizeof(signature));
206+
out_signature_buffer.reduce_size(sizeof(signature));
207+
return CHIP_NO_ERROR;
208+
}
209+
210+
EleDACProvider & EleDACProvider::GetEleDACProvider()
211+
{
212+
static EleDACProvider ele_dac_provider;
213+
214+
return ele_dac_provider;
215+
}
216+
217+
} // namespace ele
218+
} // namespace Credentials
219+
} // namespace chip
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
/*
2+
* Copyright (c) 2021 Project CHIP Authors
3+
* Copyright 2023, 2025 NXP
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
#pragma once
18+
19+
#include "hsm_api.h"
20+
#include <credentials/DeviceAttestationCredsProvider.h>
21+
22+
namespace chip {
23+
namespace Credentials {
24+
namespace ele {
25+
26+
class EleDACProvider : public DeviceAttestationCredentialsProvider
27+
{
28+
public:
29+
EleDACProvider();
30+
~EleDACProvider();
31+
static EleDACProvider & GetEleDACProvider();
32+
33+
CHIP_ERROR GetCertificationDeclaration(MutableByteSpan & out_cd_buffer) override;
34+
CHIP_ERROR GetFirmwareInformation(MutableByteSpan & out_firmware_info_buffer) override;
35+
CHIP_ERROR GetDeviceAttestationCert(MutableByteSpan & out_dac_buffer) override;
36+
CHIP_ERROR GetProductAttestationIntermediateCert(MutableByteSpan & out_pai_buffer) override;
37+
CHIP_ERROR SignWithDeviceAttestationKey(const ByteSpan & message_to_sign, MutableByteSpan & out_signature_buffer) override;
38+
39+
private:
40+
hsm_hdl_t hsm_session_hdl = 0;
41+
hsm_hdl_t key_store_hdl = 0;
42+
};
43+
44+
} // namespace ele
45+
} // namespace Credentials
46+
} // namespace chip

examples/platform/linux/DeviceAttestationCreds.cpp examples/platform/linux/DeviceAttestationCredsTrusty.cpp

+2-3
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
/*
22
*
33
* Copyright (c) 2021-2022 Project CHIP Authors
4+
* Copyright 2023, 2025 NXP
45
*
56
* Licensed under the Apache License, Version 2.0 (the "License");
67
* you may not use this file except in compliance with the License.
@@ -13,10 +14,8 @@
1314
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1415
* See the License for the specific language governing permissions and
1516
* limitations under the License.
16-
*
17-
* Copyright 2023 NXP
1817
*/
19-
#include "DeviceAttestationCreds.h"
18+
#include "DeviceAttestationCredsTrusty.h"
2019

2120
#include <crypto/CHIPCryptoPAL.h>
2221
#include <lib/core/CHIPError.h>

examples/platform/linux/DeviceAttestationCreds.h examples/platform/linux/DeviceAttestationCredsTrusty.h

+1-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
/*
2-
* Copyright 2023 NXP
3-
*
42
* Copyright (c) 2021 Project CHIP Authors
3+
* Copyright 2023, 2025 NXP
54
*
65
* Licensed under the Apache License, Version 2.0 (the "License");
76
* you may not use this file except in compliance with the License.

examples/platform/linux/PersistentStorageOperationalKeystoreEle.cpp

+3-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
/*
22
* Copyright (c) 2022 Project CHIP Authors
3+
* Copyright 2023, 2025 NXP
34
* All rights reserved.
45
*
56
* Licensed under the Apache License, Version 2.0 (the "License");
@@ -13,8 +14,6 @@
1314
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1415
* See the License for the specific language governing permissions and
1516
* limitations under the License.
16-
*
17-
* Copyright 2023 NXP
1817
*/
1918

2019
#include <crypto/OperationalKeystore.h>
@@ -76,12 +75,12 @@ PersistentStorageOperationalKeystoreEle::PersistentStorageOperationalKeystoreEle
7675
open_svc_key_store_args.key_store_identifier = KEY_STORE_ID;
7776
open_svc_key_store_args.authentication_nonce = AUTHEN_NONCE;
7877
// try to create a new keystore, if it already exist, open it
79-
open_svc_key_store_args.flags = 1;
78+
open_svc_key_store_args.flags = (HSM_SVC_KEY_STORE_FLAGS_CREATE | HSM_SVC_KEY_STORE_FLAGS_STRICT_OPERATION);
8079
err = hsm_open_key_store_service(hsm_session_hdl, &open_svc_key_store_args, &key_store_hdl);
8180
if (err == HSM_KEY_STORE_CONFLICT)
8281
{
8382
ChipLogDetail(Crypto, "keystore already existed, open it...\n");
84-
open_svc_key_store_args.flags = 0;
83+
open_svc_key_store_args.flags = HSM_SVC_KEY_STORE_FLAGS_LOAD;
8584
err = hsm_open_key_store_service(hsm_session_hdl, &open_svc_key_store_args, &key_store_hdl);
8685
if (err != HSM_NO_ERROR)
8786
{

0 commit comments

Comments
 (0)