22
22
#include < algorithm>
23
23
#include < memory>
24
24
25
+ #include " JniReferences.h"
26
+ #include < support/CodeUtils.h>
27
+
25
28
#include < platform/KeyValueStoreManager.h>
26
29
#include < support/ThreadOperationalDataset.h>
27
30
28
31
using namespace chip ::Controller;
29
32
30
33
extern chip::Ble::BleLayer * GetJNIBleLayer ();
31
34
35
+ constexpr const char kOperationalCredentialsIssuerKeypairStorage [] = " AndroidDeviceControllerKey" ;
32
36
AndroidDeviceControllerWrapper::~AndroidDeviceControllerWrapper ()
33
37
{
34
38
if ((mJavaVM != nullptr ) && (mJavaObjectRef != nullptr ))
@@ -50,6 +54,15 @@ void AndroidDeviceControllerWrapper::CallJavaMethod(const char * methodName, jin
50
54
argument);
51
55
}
52
56
57
+ CHIP_ERROR AndroidDeviceControllerWrapper::GetRootCACertificate (chip::FabricId fabricId, uint8_t * certBuf, uint32_t certBufSize,
58
+ uint32_t & outCertLen)
59
+ {
60
+ Initialize ();
61
+ VerifyOrReturnError (mInitialized , CHIP_ERROR_INCORRECT_STATE);
62
+ chip::X509CertRequestParams newCertParams = { 0 , mIssuerId , mNow , mNow + mValidity , true , fabricId, false , 0 };
63
+ return NewRootX509Cert (newCertParams, mIssuer , certBuf, certBufSize, outCertLen);
64
+ }
65
+
53
66
AndroidDeviceControllerWrapper * AndroidDeviceControllerWrapper::AllocateNew (JavaVM * vm, jobject deviceControllerObj,
54
67
pthread_mutex_t * stackLock, chip::NodeId nodeId,
55
68
chip::System::Layer * systemLayer,
@@ -90,20 +103,19 @@ AndroidDeviceControllerWrapper * AndroidDeviceControllerWrapper::AllocateNew(Jav
90
103
91
104
chip::Controller::CommissionerInitParams initParams;
92
105
93
- initParams.storageDelegate = wrapper.get ();
94
- initParams.pairingDelegate = wrapper.get ();
95
- initParams.systemLayer = systemLayer;
96
- initParams.inetLayer = inetLayer;
97
- initParams.bleLayer = GetJNIBleLayer ();
106
+ initParams.storageDelegate = wrapper.get ();
107
+ initParams.pairingDelegate = wrapper.get ();
108
+ initParams.operationalCredentialsDelegate = wrapper.get ();
109
+ initParams.systemLayer = systemLayer;
110
+ initParams.inetLayer = inetLayer;
111
+ initParams.bleLayer = GetJNIBleLayer ();
98
112
99
113
*errInfoOnFailure = wrapper->OpCredsIssuer ().Initialize (*initParams.storageDelegate );
100
114
if (*errInfoOnFailure != CHIP_NO_ERROR)
101
115
{
102
116
return nullptr ;
103
117
}
104
118
105
- initParams.operationalCredentialsDelegate = &wrapper->OpCredsIssuer ();
106
-
107
119
*errInfoOnFailure = wrapper->Controller ()->Init (nodeId, initParams);
108
120
109
121
if (*errInfoOnFailure != CHIP_NO_ERROR)
@@ -139,6 +151,69 @@ void AndroidDeviceControllerWrapper::OnPairingDeleted(CHIP_ERROR error)
139
151
CallJavaMethod (" onPairingDeleted" , static_cast <jint>(error));
140
152
}
141
153
154
+ // TODO Refactor this API to match latest spec, so that GenerateNodeOperationalCertificate receives the full CSR Elements data
155
+ // payload.
156
+ CHIP_ERROR AndroidDeviceControllerWrapper::GenerateNodeOperationalCertificate (const chip::PeerId & peerId,
157
+ const chip::ByteSpan & csr, int64_t serialNumber,
158
+ uint8_t * certBuf, uint32_t certBufSize,
159
+ uint32_t & outCertLen)
160
+ {
161
+ jmethodID method;
162
+ CHIP_ERROR err = CHIP_NO_ERROR;
163
+ err = JniReferences::GetInstance ().FindMethod (JniReferences::GetInstance ().GetEnvForCurrentThread (), mJavaObjectRef ,
164
+ " onOpCSRGenerationComplete" , " ([B)V" , &method);
165
+ if (err != CHIP_NO_ERROR)
166
+ {
167
+ ChipLogError (Controller, " Error invoking onOpCSRGenerationComplete: %d" , err);
168
+ return err;
169
+ }
170
+
171
+ // Initializing the KeyPair.
172
+ Initialize ();
173
+
174
+ chip::X509CertRequestParams request = { serialNumber, mIssuerId , mNow , mNow + mValidity , true , peerId.GetFabricId (),
175
+ true , peerId.GetNodeId () };
176
+
177
+ chip::P256PublicKey pubkey;
178
+ ReturnErrorOnFailure (VerifyCertificateSigningRequest (csr.data (), csr.size (), pubkey));
179
+
180
+ ChipLogProgress (chipTool, " VerifyCertificateSigningRequest" );
181
+
182
+ CHIP_ERROR generateCert = NewNodeOperationalX509Cert (request, chip::CertificateIssuerLevel::kIssuerIsRootCA , pubkey, mIssuer ,
183
+ certBuf, certBufSize, outCertLen);
184
+ jbyteArray argument;
185
+ JniReferences::GetInstance ().GetEnvForCurrentThread ()->ExceptionClear ();
186
+ JniReferences::GetInstance ().N2J_ByteArray (JniReferences::GetInstance ().GetEnvForCurrentThread (), csr.data (), csr.size (),
187
+ argument);
188
+ JniReferences::GetInstance ().GetEnvForCurrentThread ()->CallVoidMethod (mJavaObjectRef , method, argument);
189
+ return generateCert;
190
+ }
191
+
192
+ CHIP_ERROR AndroidDeviceControllerWrapper::Initialize ()
193
+ {
194
+ chip::Crypto::P256SerializedKeypair serializedKey;
195
+ uint16_t keySize = static_cast <uint16_t >(sizeof (serializedKey));
196
+
197
+ // TODO: Use Android keystore system instead of direct storage of private key and add specific errors to check if a specified
198
+ // item is not found in the keystore.
199
+ if (SyncGetKeyValue (kOperationalCredentialsIssuerKeypairStorage , &serializedKey, keySize) != CHIP_NO_ERROR)
200
+ {
201
+ // If storage doesn't have an existing keypair, create one and add it to the storage.
202
+ ReturnErrorOnFailure (mIssuer .Initialize ());
203
+ ReturnErrorOnFailure (mIssuer .Serialize (serializedKey));
204
+ keySize = static_cast <uint16_t >(sizeof (serializedKey));
205
+ SyncSetKeyValue (kOperationalCredentialsIssuerKeypairStorage , &serializedKey, keySize);
206
+ }
207
+ else
208
+ {
209
+ // Use the keypair from the storage
210
+ ReturnErrorOnFailure (mIssuer .Deserialize (serializedKey));
211
+ }
212
+
213
+ mInitialized = true ;
214
+ return CHIP_NO_ERROR;
215
+ }
216
+
142
217
void AndroidDeviceControllerWrapper::OnMessage (chip::System::PacketBufferHandle && msg) {}
143
218
144
219
void AndroidDeviceControllerWrapper::OnStatusChange (void ) {}
0 commit comments