/* * * Copyright (c) 2022 Project CHIP Authors * All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #include #include #include #include #include #include using namespace chip; using namespace chip::Credentials; typedef void PyObject; using namespace chip; extern "C" { typedef void (*pychip_DeviceController_IssueNOCChainCallbackPythonCallback)( PyObject * context, PyChipError status, const uint8_t * noc, size_t nocLen, const uint8_t * icac, size_t icacLen, const uint8_t * rcac, size_t rcacLen, const uint8_t * ipk, size_t ipkLen, NodeId adminSubject); static pychip_DeviceController_IssueNOCChainCallbackPythonCallback pychip_DeviceController_IssueNOCChainCallbackPythonCallbackFunct; void pychip_DeviceController_SetIssueNOCChainCallbackPythonCallback( pychip_DeviceController_IssueNOCChainCallbackPythonCallback callback) { pychip_DeviceController_IssueNOCChainCallbackPythonCallbackFunct = callback; } PyChipError pychip_DeviceController_IssueNOCChain(chip::Controller::DeviceCommissioner * devCtrl, PyObject * pythonContext, uint8_t * NOCSRElements, size_t NOCSRElementsLen, NodeId nodeId); } void pychip_DeviceController_IssueNOCChainCallback(void * context, CHIP_ERROR status, const ByteSpan & noc, const ByteSpan & icac, const ByteSpan & rcac, Optional ipk, Optional adminSubject) { if (pychip_DeviceController_IssueNOCChainCallbackPythonCallbackFunct == nullptr) { return; } chip::Platform::ScopedMemoryBuffer chipNoc; chip::Platform::ScopedMemoryBuffer chipIcac; chip::Platform::ScopedMemoryBuffer chipRcac; MutableByteSpan chipNocSpan; MutableByteSpan chipIcacSpan; MutableByteSpan chipRcacSpan; CHIP_ERROR err = status; if (err != CHIP_NO_ERROR) { ExitNow(); } VerifyOrExit(chipNoc.Alloc(Credentials::kMaxCHIPCertLength), err = CHIP_ERROR_NO_MEMORY); chipNocSpan = MutableByteSpan(chipNoc.Get(), Credentials::kMaxCHIPCertLength); VerifyOrExit(chipIcac.Alloc(Credentials::kMaxCHIPCertLength), err = CHIP_ERROR_NO_MEMORY); chipIcacSpan = MutableByteSpan(chipIcac.Get(), Credentials::kMaxCHIPCertLength); VerifyOrExit(chipRcac.Alloc(Credentials::kMaxCHIPCertLength), err = CHIP_ERROR_NO_MEMORY); chipRcacSpan = MutableByteSpan(chipRcac.Get(), Credentials::kMaxCHIPCertLength); SuccessOrExit(err = ConvertX509CertToChipCert(noc, chipNocSpan)); SuccessOrExit(err = ConvertX509CertToChipCert(icac, chipIcacSpan)); SuccessOrExit(err = ConvertX509CertToChipCert(rcac, chipRcacSpan)); exit: if (err == CHIP_NO_ERROR) { pychip_DeviceController_IssueNOCChainCallbackPythonCallbackFunct( context, ToPyChipError(err), chipNocSpan.data(), chipNocSpan.size(), chipIcacSpan.data(), chipIcacSpan.size(), chipRcacSpan.data(), chipRcacSpan.size(), ipk.HasValue() ? ipk.Value().data() : nullptr, ipk.HasValue() ? ipk.Value().size() : 0, adminSubject.ValueOr(kUndefinedNodeId)); } else { pychip_DeviceController_IssueNOCChainCallbackPythonCallbackFunct(context, ToPyChipError(err), nullptr, 0, nullptr, 0, nullptr, 0, nullptr, 0, 0); } } PyChipError pychip_DeviceController_IssueNOCChain(chip::Controller::DeviceCommissioner * devCtrl, PyObject * pythonContext, uint8_t * NOCSRElements, size_t NOCSRElementsLen, NodeId nodeId) { return ToPyChipError(devCtrl->IssueNOCChain( ByteSpan(NOCSRElements, NOCSRElementsLen), nodeId, /* Note: Memory leak here. This is a quick and a bit dirty PoC */ new Callback::Callback(pychip_DeviceController_IssueNOCChainCallback, pythonContext))); }