From aae22c111df15665e1686682500d10b8adc5b5e6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ren=C3=A9=20Josefsen?= <69624991+ReneJosefsen@users.noreply.github.com> Date: Wed, 6 Mar 2024 13:44:32 +0100 Subject: [PATCH 1/6] PICS Generator tool update (#30866) * Fixed missed cluster renaming and adjusted output folder behavior * Minor adjustments to readme to match the proper location of tool * Fix restyle * Reverted laundry mode due to rename revert * Fully remove laundry mode cluster handling * Use DM XML for PICS code rather than cluster data file * Remove unused import * Remove uncommented code * Update special cluster handling and fixed crash when node is not present in PICS XML * Added special handling for Laundry clusters * Improved handling for non standard clusters * Updated handling for special cluster names * Updated Access Control handling * Remove space in AccessControl * Added handling for ICDManagement * Fix bug in if statement syntax * Minor updates to match spring 2024 SVE PICS --- src/tools/PICS-generator/PICSGenerator.py | 241 +++++++++++----------- src/tools/PICS-generator/README.md | 19 +- 2 files changed, 132 insertions(+), 128 deletions(-) diff --git a/src/tools/PICS-generator/PICSGenerator.py b/src/tools/PICS-generator/PICSGenerator.py index aa774f9cb127e3..2a3f3613274245 100644 --- a/src/tools/PICS-generator/PICSGenerator.py +++ b/src/tools/PICS-generator/PICSGenerator.py @@ -16,7 +16,6 @@ # import argparse -import json import os import pathlib import sys @@ -28,8 +27,10 @@ # Add the path to python_testing folder, in order to be able to import from matter_testing_support sys.path.append(os.path.abspath(sys.path[0] + "/../../python_testing")) from matter_testing_support import MatterBaseTest, async_test_body, default_matter_test_main # noqa: E402 +from spec_parsing_support import build_xml_clusters # noqa: E402 console = None +xml_clusters = None def GenerateDevicePicsXmlFiles(clusterName, clusterPicsCode, featurePicsList, attributePicsList, acceptedCommandPicsList, generatedCommandPicsList, outputPathStr): @@ -37,28 +38,39 @@ def GenerateDevicePicsXmlFiles(clusterName, clusterPicsCode, featurePicsList, at xmlPath = xmlTemplatePathStr fileName = "" - print(f"Handling PICS for {clusterName}") + console.print(f"Handling PICS for {clusterName}") # Map clusters to common XML template if needed - otaProviderCluster = "OTA Software Update Provider Cluster" - otaRequestorCluster = "OTA Software Update Requestor Cluster" - onOffCluster = "On/Off Cluster" - groupKeyManagementCluster = "Group Key Management Cluster" - nodeOperationalCredentialsCluster = "Node Operational Credentials Cluster" - basicInformationCluster = "Basic Information Cluster" - networkCommissioningCluster = "Network Commissioning Cluster" - - if otaProviderCluster in clusterName or otaRequestorCluster in clusterName: + if "ICDManagement" == clusterName: + clusterName = "ICD Management" + + elif "OTA Software Update Provider" in clusterName or "OTA Software Update Requestor" in clusterName: clusterName = "OTA Software Update" - elif onOffCluster == clusterName: + elif "On/Off" == clusterName: clusterName = clusterName.replace("/", "-") - elif groupKeyManagementCluster == clusterName: + elif "Group Key Management" == clusterName: clusterName = "Group Communication" - elif nodeOperationalCredentialsCluster == clusterName or basicInformationCluster == clusterName or networkCommissioningCluster == clusterName: - clusterName = clusterName.replace("Cluster", "").strip() + elif "Wake On LAN" == clusterName or "Low Power" == clusterName: + clusterName = "Media Cluster" + + elif "Operational Credentials" == clusterName: + clusterName = "Node Operational Credentials" + + elif "Laundry Washer Controls" == clusterName: + clusterName = "Washer Controls" + + # Workaround for naming colisions with current logic + elif "Thermostat" == clusterName: + clusterName = "Thermostat Cluster" + + elif "Boolean State" == clusterName: + clusterName = "Boolean State Cluster" + + if "AccessControl" in clusterName: + clusterName = "Access Control cluster" # Determine if file has already been handled and use this file for outputFolderFileName in os.listdir(outputPathStr): @@ -108,57 +120,61 @@ def GenerateDevicePicsXmlFiles(clusterName, clusterPicsCode, featurePicsList, at # Feature PICS # console.print(featurePicsList) featureNode = root.find("./clusterSide[@type='Server']/features") - for picsItem in featureNode: - itemNumberElement = picsItem.find('itemNumber') + if featureNode is not None: + for picsItem in featureNode: + itemNumberElement = picsItem.find('itemNumber') - console.print(f"Searching for {itemNumberElement.text}") + console.print(f"Searching for {itemNumberElement.text}") - if f"{itemNumberElement.text}" in featurePicsList: - console.print("Found feature PICS value in XML template ✅") - supportElement = picsItem.find('support') - supportElement.text = "true" + if f"{itemNumberElement.text}" in featurePicsList: + console.print("Found feature PICS value in XML template ✅") + supportElement = picsItem.find('support') + supportElement.text = "true" # Attributes PICS # TODO: Only check if list is not empty # console.print(attributePicsList) serverAttributesNode = root.find("./clusterSide[@type='Server']/attributes") - for picsItem in serverAttributesNode: - itemNumberElement = picsItem.find('itemNumber') + if serverAttributesNode is not None: + for picsItem in serverAttributesNode: + itemNumberElement = picsItem.find('itemNumber') - console.print(f"Searching for {itemNumberElement.text}") + console.print(f"Searching for {itemNumberElement.text}") - if f"{itemNumberElement.text}" in attributePicsList: - console.print("Found attribute PICS value in XML template ✅") - supportElement = picsItem.find('support') - supportElement.text = "true" + if f"{itemNumberElement.text}" in attributePicsList: + console.print("Found attribute PICS value in XML template ✅") + supportElement = picsItem.find('support') + supportElement.text = "true" # AcceptedCommandList PICS # TODO: Only check if list is not empty # console.print(acceptedCommandPicsList) serverCommandsReceivedNode = root.find("./clusterSide[@type='Server']/commandsReceived") - for picsItem in serverCommandsReceivedNode: - itemNumberElement = picsItem.find('itemNumber') + if serverCommandsReceivedNode is not None: + for picsItem in serverCommandsReceivedNode: + itemNumberElement = picsItem.find('itemNumber') - console.print(f"Searching for {itemNumberElement.text}") + console.print(f"Searching for {itemNumberElement.text}") - if f"{itemNumberElement.text}" in acceptedCommandPicsList: - console.print("Found acceptedCommand PICS value in XML template ✅") - supportElement = picsItem.find('support') - supportElement.text = "true" + if f"{itemNumberElement.text}" in acceptedCommandPicsList: + console.print("Found acceptedCommand PICS value in XML template ✅") + supportElement = picsItem.find('support') + supportElement.text = "true" # GeneratedCommandList PICS # console.print(generatedCommandPicsList) # TODO: Only check if list is not empty serverCommandsGeneratedNode = root.find("./clusterSide[@type='Server']/commandsGenerated") - for picsItem in serverCommandsGeneratedNode: - itemNumberElement = picsItem.find('itemNumber') + if serverCommandsGeneratedNode is not None: + for picsItem in serverCommandsGeneratedNode: + itemNumberElement = picsItem.find('itemNumber') - console.print(f"Searching for {itemNumberElement.text}") + console.print(f"Searching for {itemNumberElement.text}") - if f"{itemNumberElement.text}" in generatedCommandPicsList: - console.print("Found generatedCommand PICS value in XML template ✅") - supportElement = picsItem.find('support') - supportElement.text = "true" + if f"{itemNumberElement.text}" in generatedCommandPicsList: + console.print("Found generatedCommand PICS value in XML template ✅") + supportElement = picsItem.find('support') + supportElement.text = "true" # Event PICS (Work in progress) # The ability to set event PICS is fairly limited, due to EventList not being supported, @@ -168,35 +184,36 @@ def GenerateDevicePicsXmlFiles(clusterName, clusterPicsCode, featurePicsList, at # 1) Event is mandatody # 2) The event is mandatory based on a feature that is supported (Cross check against feature list) (Not supported yet) serverEventsNode = root.find("./clusterSide[@type='Server']/events") - for picsItem in serverEventsNode: - itemNumberElement = picsItem.find('itemNumber') - statusElement = picsItem.find('status') - - try: - condition = statusElement.attrib['cond'] - console.print(f"Checking {itemNumberElement.text} with conformance {statusElement.text} and condition {condition}") - except ET.ParseError: - condition = "" - console.print(f"Checking {itemNumberElement.text} with conformance {statusElement.text}") - - if statusElement.text == "M": - - # Is event mandated by the server - if condition == clusterPicsCode: - console.print("Found event mandated by server ✅") - supportElement = picsItem.find('support') - supportElement.text = "true" - continue - - if condition in featurePicsList: - console.print("Found event mandated by feature ✅") - supportElement = picsItem.find('support') - supportElement.text = "true" - continue - - if condition == "": - console.print("Event is mandated without a condition ✅") - continue + if serverEventsNode is not None: + for picsItem in serverEventsNode: + itemNumberElement = picsItem.find('itemNumber') + statusElement = picsItem.find('status') + + try: + condition = statusElement.attrib['cond'] + console.print(f"Checking {itemNumberElement.text} with conformance {statusElement.text} and condition {condition}") + except ET.ParseError: + condition = "" + console.print(f"Checking {itemNumberElement.text} with conformance {statusElement.text}") + + if statusElement.text == "M": + + # Is event mandated by the server + if condition == clusterPicsCode: + console.print("Found event mandated by server ✅") + supportElement = picsItem.find('support') + supportElement.text = "true" + continue + + if condition in featurePicsList: + console.print("Found event mandated by feature ✅") + supportElement = picsItem.find('support') + supportElement.text = "true" + continue + + if condition == "": + console.print("Event is mandated without a condition ✅") + continue # Grabbing the header from the XML templates inputFile = open(f"{xmlPath}{fileName}", "r") @@ -255,21 +272,28 @@ async def DeviceMapping(devCtrl, nodeID, outputPathStr): acceptedCommandListPicsList = [] generatedCommandListPicsList = [] - clusterClass = getattr(Clusters, devCtrl.GetClusterHandler().GetClusterInfoById(server)['clusterName']) clusterID = f"0x{server:04x}" - # Does the clusterInfoDict contain the found cluster ID? - if clusterID not in clusterInfoDict: - console.print(f"[red]Cluster ID ({clusterID}) not in list! ❌") + if server > 0x7FFF: + console.print(f"[red]Cluster outside standard range ({clusterID}) not handled! ❌") continue - clusterName = clusterInfoDict[clusterID]['Name'] - clusterPICS = f"{clusterInfoDict[clusterID]['PICS_Code']}{serverTag}" + try: + clusterClass = getattr(Clusters, devCtrl.GetClusterHandler().GetClusterInfoById(server)['clusterName']) + except AttributeError: + console.print(f"[red]Cluster class not found for ({clusterID}) not found! ❌") + continue - console.print(f"{clusterName} - {clusterPICS}") + # Does the the DM XML contain the found cluster ID? + try: + clusterName = xml_clusters[server].name + clusterPICS = f"{xml_clusters[server].pics}{serverTag}" + + except KeyError: + console.print(f"[red]Cluster ({clusterID}) not found in DM XML! ❌") + continue - # Print PICS for specific server from dict - # console.print(clusterInfoDict[f"0x{server:04x}"]) + console.print(f"{clusterName} - {clusterPICS}") # Read feature map featureMapResponse = await devCtrl.ReadAttribute(nodeID, [(endpoint, clusterClass.Attributes.FeatureMap)]) @@ -339,8 +363,14 @@ async def DeviceMapping(devCtrl, nodeID, outputPathStr): for client in clientList: clusterID = f"0x{client:04x}" - clusterName = clusterInfoDict[clusterID]['Name'] - clusterPICS = f"{clusterInfoDict[clusterID]['PICS_Code']}{clientTag}" + + try: + clusterName = xml_clusters[client].name + clusterPICS = f"{xml_clusters[client].pics}{clientTag}" + + except KeyError: + console.print(f"[red]Cluster ({clusterID}) not found in DM XML! ❌") + continue console.print(f"{clusterName} - {clusterPICS}") @@ -357,14 +387,10 @@ def cleanDirectory(pathToClean): parser = argparse.ArgumentParser() -parser.add_argument('--cluster-data', required=True) parser.add_argument('--pics-template', required=True) parser.add_argument('--pics-output', required=True) args, unknown = parser.parse_known_args() -basePath = os.path.dirname(__file__) -clusterInfoInputPathStr = args.cluster_data - xmlTemplatePathStr = args.pics_template if not xmlTemplatePathStr.endswith('/'): xmlTemplatePathStr += '/' @@ -372,6 +398,7 @@ def cleanDirectory(pathToClean): baseOutputPathStr = args.pics_output if not baseOutputPathStr.endswith('/'): baseOutputPathStr += '/' +outputPathStr = baseOutputPathStr + "GeneratedPICS/" serverTag = ".S" clientTag = ".C" @@ -391,43 +418,20 @@ def cleanDirectory(pathToClean): # Endpoint define rootNodeEndpointID = 0 -# Load cluster info -inputJson = {} -clusterInfoDict = {} - -print("Generating cluster data dict from JSON input") - -with open(clusterInfoInputPathStr, 'rb') as clusterInfoInputFile: - clusterInfoJson = json.load(clusterInfoInputFile) - - for cluster in clusterInfoJson: - clusterData = clusterInfoJson[f"{cluster}"]["Data created by Script"] - - try: - # Check if cluster id is a value hex value - clusterIdValid = int(clusterData["Id"].lower(), 16) - - # Add cluster data to dict - clusterInfoDict[clusterData["Id"].lower()] = { - "Name": clusterData["Cluster Name"], - "PICS_Code": clusterData["PICS Code"], - } - - except ValueError: - print(f"Ignore ClusterID: {clusterData['Id']} - {clusterData['Cluster Name']}") - # Load PICS XML templates print("Capture list of PICS XML templates") xmlFileList = os.listdir(xmlTemplatePathStr) # Setup output path -baseOutputPath = pathlib.Path(baseOutputPathStr) -if not baseOutputPath.exists(): +print(outputPathStr) + +outputPath = pathlib.Path(outputPathStr) +if not outputPath.exists(): print("Create output folder") - baseOutputPath.mkdir() + outputPath.mkdir() else: print("Clean output folder") - cleanDirectory(baseOutputPath) + cleanDirectory(outputPath) class DeviceMappingTest(MatterBaseTest): @@ -438,8 +442,11 @@ async def test_device_mapping(self): global console console = Console() + global xml_clusters + xml_clusters, problems = build_xml_clusters() + # Run device mapping function - await DeviceMapping(self.default_controller, self.dut_node_id, baseOutputPathStr) + await DeviceMapping(self.default_controller, self.dut_node_id, outputPathStr) if __name__ == "__main__": diff --git a/src/tools/PICS-generator/README.md b/src/tools/PICS-generator/README.md index 1f5964d80e9b5e..9c20616bb5bc0a 100644 --- a/src/tools/PICS-generator/README.md +++ b/src/tools/PICS-generator/README.md @@ -30,13 +30,6 @@ Once the python environment is build it can be activated using this command: source out/python_env/bin/activate ``` -The script uses the json based data model in order to convert cluster -identifiers into PICS Codes. The file can be downloaded here: -[https://groups.csa-iot.org/wg/matter-csg/document/27290](https://groups.csa-iot.org/wg/matter-csg/document/27290) - -NOTE: The tool has been verified using the "Specification_version -0.7-spring2024.json" version. - The script uses the PICS XML templates for generate the PICS output. These files can be downloaded here: [https://groups.csa-iot.org/wg/matter-csg/document/26122](https://groups.csa-iot.org/wg/matter-csg/document/26122) @@ -46,11 +39,15 @@ certification) # How to run +First change the directory to the tool location. + +``` +cd src/tools/PICS-generator/ +``` + The tool does, as mentioned above, have external dependencies, these are provided to the tool using these arguments: -- --cluster-data is the absolute path to the JSON file containing the cluster - data - --pics-template is the absolute path to the folder containing the PICS templates - --pics-output is the absolute path to the output folder to be used @@ -59,7 +56,7 @@ If the device has not been commissioned this can be done by passing in the commissioning information: ``` -python3 'src/python_testing/PICSGenerator.py' --cluster-data --pics-template --pics-output --commissioning-method ble-thread --discriminator --passcode --thread-dataset-hex +python3 PICSGenerator.py --pics-template --pics-output --commissioning-method ble-thread --discriminator --passcode --thread-dataset-hex ``` In case the device uses a development PAA, the following parameter should be @@ -79,5 +76,5 @@ added. If a device has already been commissioned, the tool can be executed like this: ``` -python3 'src/python_testing/PICSGenerator.py' --cluster-data --pics-template --pics-output +python3 PICSGenerator.py --pics-template --pics-output ``` From e48ed00c4b202cd97a628e40287069c2cb668572 Mon Sep 17 00:00:00 2001 From: Yufeng Wang Date: Wed, 6 Mar 2024 09:52:49 -0800 Subject: [PATCH 2/6] Remove unused dependency (#32453) --- src/controller/java/BUILD.gn | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/controller/java/BUILD.gn b/src/controller/java/BUILD.gn index a2f3c866bdaa76..21e667716bbcb2 100644 --- a/src/controller/java/BUILD.gn +++ b/src/controller/java/BUILD.gn @@ -365,11 +365,7 @@ kotlin_library("kotlin_matter_controller") { output_name = "KotlinMatterController.jar" - deps = [ - ":java", - ":tlv", - "${chip_root}/third_party/java_deps:annotation", - ] + deps = [ ":java" ] sources = [ "src/matter/controller/CompletionListenerAdapter.kt", From b742587091630534313e0403d87c649db690496d Mon Sep 17 00:00:00 2001 From: Boris Zbarsky Date: Wed, 6 Mar 2024 13:47:17 -0500 Subject: [PATCH 3/6] Fix loading of CD signing certs in chip-tool. (#32395) We were calling a function that tried to validate that the certs are valid PAA certs, which is very much not required for CD signing certs. Fixes https://github.com/project-chip/connectedhomeip/issues/32337 --- .../chip-tool/commands/common/CHIPCommand.cpp | 3 +- .../FileAttestationTrustStore.cpp | 34 ++++++++++++++----- .../FileAttestationTrustStore.h | 16 +++++++-- 3 files changed, 42 insertions(+), 11 deletions(-) diff --git a/examples/chip-tool/commands/common/CHIPCommand.cpp b/examples/chip-tool/commands/common/CHIPCommand.cpp index 125ab46433e0ef..29de06b5e0069c 100644 --- a/examples/chip-tool/commands/common/CHIPCommand.cpp +++ b/examples/chip-tool/commands/common/CHIPCommand.cpp @@ -166,7 +166,8 @@ CHIP_ERROR CHIPCommand::MaybeSetUpStack() cdTrustStorePath = getenv(kCDTrustStorePathVariable); } - auto additionalCdCerts = chip::Credentials::LoadAllX509DerCerts(cdTrustStorePath); + auto additionalCdCerts = + chip::Credentials::LoadAllX509DerCerts(cdTrustStorePath, chip::Credentials::CertificateValidationMode::kPublicKeyOnly); if (cdTrustStorePath != nullptr && additionalCdCerts.size() == 0) { ChipLogError(chipTool, "Warning: no CD signing certs found in path: %s, only defaults will be used", cdTrustStorePath); diff --git a/src/credentials/attestation_verifier/FileAttestationTrustStore.cpp b/src/credentials/attestation_verifier/FileAttestationTrustStore.cpp index c5e59153491378..7707cb4d2aa495 100644 --- a/src/credentials/attestation_verifier/FileAttestationTrustStore.cpp +++ b/src/credentials/attestation_verifier/FileAttestationTrustStore.cpp @@ -53,7 +53,7 @@ FileAttestationTrustStore::FileAttestationTrustStore(const char * paaTrustStoreP mIsInitialized = true; } -std::vector> LoadAllX509DerCerts(const char * trustStorePath) +std::vector> LoadAllX509DerCerts(const char * trustStorePath, CertificateValidationMode validationMode) { std::vector> certs; if (trustStorePath == nullptr) @@ -89,21 +89,39 @@ std::vector> LoadAllX509DerCerts(const char * trustStorePat if ((certificateLength > 0) && (certificateLength <= kMaxDERCertLength)) { certificate.resize(certificateLength); - // Only accumulate certificate if it has a subject key ID extension - { - uint8_t kidBuf[Crypto::kSubjectKeyIdentifierLength] = { 0 }; - MutableByteSpan kidSpan{ kidBuf }; - ByteSpan certSpan{ certificate.data(), certificate.size() }; + ByteSpan certSpan{ certificate.data(), certificate.size() }; + // Only accumulate certificate if it passes validation. + bool isValid = false; + switch (validationMode) + { + case CertificateValidationMode::kPAA: { if (CHIP_NO_ERROR != VerifyAttestationCertificateFormat(certSpan, Crypto::AttestationCertType::kPAA)) { - continue; + break; } + uint8_t kidBuf[Crypto::kSubjectKeyIdentifierLength] = { 0 }; + MutableByteSpan kidSpan{ kidBuf }; if (CHIP_NO_ERROR == Crypto::ExtractSKIDFromX509Cert(certSpan, kidSpan)) { - certs.push_back(certificate); + isValid = true; } + break; + } + case CertificateValidationMode::kPublicKeyOnly: { + Crypto::P256PublicKey publicKey; + if (CHIP_NO_ERROR == Crypto::ExtractPubkeyFromX509Cert(certSpan, publicKey)) + { + isValid = true; + } + break; + } + } + + if (isValid) + { + certs.push_back(certificate); } } fclose(file); diff --git a/src/credentials/attestation_verifier/FileAttestationTrustStore.h b/src/credentials/attestation_verifier/FileAttestationTrustStore.h index 0446d7a6ebb6b8..a0f3b974488414 100644 --- a/src/credentials/attestation_verifier/FileAttestationTrustStore.h +++ b/src/credentials/attestation_verifier/FileAttestationTrustStore.h @@ -25,17 +25,29 @@ namespace chip { namespace Credentials { +enum class CertificateValidationMode +{ + // Validate that the certificate is a valid PAA certificate. + kPAA, + // Validate just that the certificate has a public key we can extract + // (e.g. it's a CD signing certificate). + kPublicKeyOnly, +}; + /** * @brief Load all X.509 DER certificates in a given path. * - * Silently ignores non-X.509 files and X.509 files without a subject key identifier. + * Silently ignores non-X.509 files and X.509 files that fail validation as + * determined by the provided validation mode. * * Returns an empty vector if no files are found or unrecoverable errors arise. * * @param trustStorePath - path from where to search for certificates. + * @param validationMode - how the certificate files should be validated. * @return a vector of certificate DER data */ -std::vector> LoadAllX509DerCerts(const char * trustStorePath); +std::vector> LoadAllX509DerCerts(const char * trustStorePath, + CertificateValidationMode validationMode = CertificateValidationMode::kPAA); class FileAttestationTrustStore : public AttestationTrustStore { From f83409276160be0cfc679121fcd8e94f02676118 Mon Sep 17 00:00:00 2001 From: shripad621git <79364691+shripad621git@users.noreply.github.com> Date: Thu, 7 Mar 2024 10:47:55 +0530 Subject: [PATCH 4/6] [ESP32] Tracing : Added the fix of data type mismatch while registering the metrics in esp32 tracing framework. (#32355) * Fixed the type mismatch in the esp32 tracing framework * Removed the heap metrics as insights framework maps traces to heap metrics * addressed review comments * restlyed * Added a check to ensure one type associated with one key * Addressed the further review comments --- scripts/tools/check_includes_config.py | 3 ++ src/tracing/esp32_trace/esp32_tracing.cpp | 56 +++++++++++++++++++---- src/tracing/esp32_trace/esp32_tracing.h | 6 ++- 3 files changed, 54 insertions(+), 11 deletions(-) diff --git a/scripts/tools/check_includes_config.py b/scripts/tools/check_includes_config.py index f4715888832bf3..26689e4a2f85b4 100644 --- a/scripts/tools/check_includes_config.py +++ b/scripts/tools/check_includes_config.py @@ -160,6 +160,9 @@ 'src/tracing/json/json_tracing.cpp': {'string', 'sstream'}, 'src/tracing/json/json_tracing.h': {'fstream', 'unordered_map'}, + # esp32 tracing + 'src/tracing/esp32_trace/esp32_tracing.h': {'unordered_map'}, + # Not intended for embedded clients 'src/app/PendingResponseTrackerImpl.h': {'unordered_set'}, diff --git a/src/tracing/esp32_trace/esp32_tracing.cpp b/src/tracing/esp32_trace/esp32_tracing.cpp index db5f09ee9a751c..7b338466378945 100644 --- a/src/tracing/esp32_trace/esp32_tracing.cpp +++ b/src/tracing/esp32_trace/esp32_tracing.cpp @@ -17,6 +17,7 @@ */ #include +#include #include #include #include @@ -134,10 +135,7 @@ void RemoveHashFromPermitlist(const char * str) #define LOG_HEAP_INFO(label, group, entry_exit) \ do \ { \ - ESP_DIAG_EVENT("MTR_TRC", "%s - %s - %s Min Free heap - %u - LFB - %u Start free heap - %u", entry_exit, label, group, \ - heap_caps_get_minimum_free_size(MALLOC_CAP_8BIT), \ - heap_caps_get_largest_free_block(MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT), \ - heap_caps_get_free_size(MALLOC_CAP_8BIT)); \ + ESP_DIAG_EVENT("MTR_TRC", "%s - %s - %s", entry_exit, label, group); \ } while (0) void ESP32Backend::LogMessageReceived(MessageReceivedInfo & info) {} @@ -155,34 +153,71 @@ void ESP32Backend::TraceCounter(const char * label) ::Insights::ESPInsightsCounter::GetInstance(label)->ReportMetrics(); } +void ESP32Backend::RegisterMetric(const char * key, ValueType type) +{ + // Check for the same key will not have two different types. + if (mRegisteredMetrics.find(key) != mRegisteredMetrics.end()) + { + if (mRegisteredMetrics[key] != type) + { + ESP_LOGE("SYS.MTR", "Type mismatch for metric key %s", key); + return; + } + } + + switch (type) + { + case ValueType::kUInt32: + esp_diag_metrics_register("SYS_MTR" /*Tag of metrics */, key /* Unique key 8 */, key /* label displayed on dashboard */, + "insights.mtr" /* hierarchical path */, ESP_DIAG_DATA_TYPE_UINT /* data_type */); + break; + + case ValueType::kInt32: + esp_diag_metrics_register("SYS_MTR" /*Tag of metrics */, key /* Unique key 8 */, key /* label displayed on dashboard */, + "insights.mtr" /* hierarchical path */, ESP_DIAG_DATA_TYPE_INT /* data_type */); + break; + + case ValueType::kChipErrorCode: + esp_diag_metrics_register("SYS_MTR" /*Tag of metrics */, key /* Unique key 8 */, key /* label displayed on dashboard */, + "insights.mtr" /* hierarchical path */, ESP_DIAG_DATA_TYPE_UINT /* data_type */); + break; + + case ValueType::kUndefined: + ESP_LOGE("mtr", "failed to register %s as its value is undefined", key); + break; + } + + mRegisteredMetrics[key] = type; +} + void ESP32Backend::LogMetricEvent(const MetricEvent & event) { - if (!mRegistered) + if (mRegisteredMetrics.find(event.key()) == mRegisteredMetrics.end()) { - esp_diag_metrics_register("SYS_MTR" /*Tag of metrics */, event.key() /* Unique key 8 */, - event.key() /* label displayed on dashboard */, "insights.mtr" /* hierarchical path */, - ESP_DIAG_DATA_TYPE_INT /* data_type */); - mRegistered = true; + RegisterMetric(event.key(), event.ValueType()); } - using ValueType = MetricEvent::Value::Type; switch (event.ValueType()) { case ValueType::kInt32: ESP_LOGI("mtr", "The value of %s is %ld ", event.key(), event.ValueInt32()); esp_diag_metrics_add_int(event.key(), event.ValueInt32()); break; + case ValueType::kUInt32: ESP_LOGI("mtr", "The value of %s is %lu ", event.key(), event.ValueUInt32()); esp_diag_metrics_add_uint(event.key(), event.ValueUInt32()); break; + case ValueType::kChipErrorCode: ESP_LOGI("mtr", "The value of %s is error with code %lu ", event.key(), event.ValueErrorCode()); esp_diag_metrics_add_uint(event.key(), event.ValueErrorCode()); break; + case ValueType::kUndefined: ESP_LOGI("mtr", "The value of %s is undefined", event.key()); break; + default: ESP_LOGI("mtr", "The value of %s is of an UNKNOWN TYPE", event.key()); break; @@ -211,6 +246,7 @@ void ESP32Backend::TraceInstant(const char * label, const char * group) { ESP_DIAG_EVENT("MTR_TRC", "Instant : %s -%s", label, group); } + } // namespace Insights } // namespace Tracing } // namespace chip diff --git a/src/tracing/esp32_trace/esp32_tracing.h b/src/tracing/esp32_trace/esp32_tracing.h index 2e08e69d616158..c0903ac72fd8dc 100644 --- a/src/tracing/esp32_trace/esp32_tracing.h +++ b/src/tracing/esp32_trace/esp32_tracing.h @@ -1,5 +1,7 @@ #include #include +#include +#include #include namespace chip { @@ -39,7 +41,9 @@ class ESP32Backend : public ::chip::Tracing::Backend void LogMetricEvent(const MetricEvent &) override; private: - bool mRegistered = false; + using ValueType = MetricEvent::Value::Type; + std::unordered_map mRegisteredMetrics; + void RegisterMetric(const char * key, ValueType type); }; } // namespace Insights From 873e665ab6f0c0611ffbcde5263f77390f943f49 Mon Sep 17 00:00:00 2001 From: Shubham Patil Date: Thu, 7 Mar 2024 16:07:09 +0530 Subject: [PATCH 5/6] [ESP32] bump the component manager version (#32474) * [ESP32] bump the component manager version * Update requirements.esp32.txt * Update requirements.esp32.txt * fix the version in constraints.txt --- scripts/setup/constraints.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/scripts/setup/constraints.txt b/scripts/setup/constraints.txt index ad80df20c4ab24..90b80f7588af5b 100644 --- a/scripts/setup/constraints.txt +++ b/scripts/setup/constraints.txt @@ -98,7 +98,7 @@ ghapi==1.0.3 # via -r requirements.memory.txt humanfriendly==10.0 # via coloredlogs -idf-component-manager==1.2.2 +idf-component-manager==1.5.2 # via -r requirements.esp32.txt idna==3.4 # via requests From c2f58e4379410b33d98534fd0161d4f6b6229536 Mon Sep 17 00:00:00 2001 From: Jakub Latusek Date: Thu, 7 Mar 2024 13:25:18 +0100 Subject: [PATCH 6/6] Add pigweed support for nrfconnect (#32460) * Add pigweed support for nrfconnect * Restyled by gn --------- Co-authored-by: Restyled.io --- config/nrfconnect/chip-gn/.gn | 10 ++++++++++ src/BUILD.gn | 3 ++- src/test_driver/nrfconnect/main/runner.cpp | 2 ++ 3 files changed, 14 insertions(+), 1 deletion(-) diff --git a/config/nrfconnect/chip-gn/.gn b/config/nrfconnect/chip-gn/.gn index bf81e1e8f52cef..b8e1a5a86cc803 100644 --- a/config/nrfconnect/chip-gn/.gn +++ b/config/nrfconnect/chip-gn/.gn @@ -14,6 +14,7 @@ import("//build_overrides/build.gni") import("//build_overrides/chip.gni") +import("//build_overrides/pigweed.gni") # The location of the build configuration file. buildconfig = "${build_root}/config/BUILDCONFIG.gn" @@ -25,5 +26,14 @@ default_args = { target_cpu = "arm" target_os = "zephyr" + pw_sys_io_BACKEND = dir_pw_sys_io_stdio + pw_assert_BACKEND = dir_pw_assert_log + pw_log_BACKEND = dir_pw_log_basic + + pw_build_LINK_DEPS = [ + "$dir_pw_assert:impl", + "$dir_pw_log:impl", + ] + import("${chip_root}/config/nrfconnect/chip-gn/args.gni") } diff --git a/src/BUILD.gn b/src/BUILD.gn index 77eb8d362aa29a..9b9e993cc10582 100644 --- a/src/BUILD.gn +++ b/src/BUILD.gn @@ -143,7 +143,8 @@ if (chip_build_tests) { if (chip_monolithic_tests) { # TODO [PW_MIGRATION] Remove this if after migartion to PW_TEST is completed for all platforms # TODO [PW_MIGRATION] There will be a list of already migrated platforms - if (chip_device_platform == "esp32") { + if (chip_device_platform == "esp32" || + chip_device_platform == "nrfconnect") { deps += [ "${chip_root}/src/lib/support:pw_tests_wrapper" ] } build_monolithic_library = true diff --git a/src/test_driver/nrfconnect/main/runner.cpp b/src/test_driver/nrfconnect/main/runner.cpp index 99848e423c1390..1cd57d0bbbd406 100644 --- a/src/test_driver/nrfconnect/main/runner.cpp +++ b/src/test_driver/nrfconnect/main/runner.cpp @@ -16,6 +16,7 @@ */ #include +#include #include #include @@ -35,6 +36,7 @@ extern "C" int main(void) LOG_INF("Starting CHIP tests!"); int status = RunRegisteredUnitTests(); + status += chip::test::RunAllTests(); LOG_INF("CHIP test status: %d", status); _exit(status);