Coverage Report

Created: 2026-03-27 06:51

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/connectedhomeip/src/app/clusters/tls-certificate-management-server/CertificateTableImpl.h
Line
Count
Source
1
/**
2
 *
3
 *    Copyright (c) 2025 Project CHIP Authors
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
18
#pragma once
19
#include <app/clusters/tls-certificate-management-server/CertificateTable.h>
20
#include <app/storage/FabricTableImpl.h>
21
#include <lib/core/CHIPConfig.h>
22
#include <lib/core/DataModelTypes.h>
23
#include <lib/support/Pool.h>
24
25
namespace chip {
26
namespace app {
27
namespace Clusters {
28
namespace Tls {
29
30
static constexpr uint16_t kMaxClientCertificatesPerFabric = CHIP_CONFIG_TLS_MAX_CLIENT_CERTS_PER_FABRIC_TABLE_SIZE;
31
static constexpr uint16_t kMaxRootCertificatesPerFabric   = CHIP_CONFIG_TLS_MAX_ROOT_PER_FABRIC_CERTS_TABLE_SIZE;
32
33
inline constexpr uint16_t kUndefinedCertificateId = 0xffff;
34
35
static_assert(kMaxClientCertificatesPerFabric >= 5, "Per spec, kMaxClientCertificatesPerFabric must be at least 5");
36
static_assert(kMaxRootCertificatesPerFabric >= 5, "Per spec, kMaxRootCertificatesPerFabric must be at least 5");
37
static_assert(kMaxClientCertificatesPerFabric <= 254, "Per spec, kMaxClientCertificatesPerFabric must be at most 254");
38
static_assert(kMaxRootCertificatesPerFabric <= 254, "Per spec, kMaxRootCertificatesPerFabric must be at most 254");
39
40
// Limit is set per-fabric
41
static constexpr uint16_t kMaxCertificatesPerEndpoint = UINT16_MAX;
42
43
/// @brief struct used to identify a certificate
44
struct CertificateId
45
{
46
    uint16_t mCertificateId = kUndefinedCertificateId;
47
48
0
    CertificateId() = default;
49
0
    CertificateId(uint16_t id) : mCertificateId(id) {}
50
51
0
    void Clear() { mCertificateId = kUndefinedCertificateId; }
52
53
0
    bool IsValid() { return (mCertificateId != kUndefinedCertificateId); }
54
55
0
    uint16_t & Value() { return mCertificateId; }
56
0
    const uint16_t & Value() const { return mCertificateId; }
57
58
0
    bool operator==(const CertificateId & other) const { return (mCertificateId == other.mCertificateId); }
59
};
60
61
class RootCertificateTable : public app::Storage::FabricTableImpl<CertificateId, CertificateTable::RootCertStruct>
62
{
63
public:
64
    using Super = app::Storage::FabricTableImpl<CertificateId, CertificateTable::RootCertStruct>;
65
66
0
    RootCertificateTable() : Super(kMaxRootCertificatesPerFabric, kMaxCertificatesPerEndpoint) {}
67
0
    ~RootCertificateTable() { Finish(); };
68
};
69
70
class ClientCertificateTable : public app::Storage::FabricTableImpl<CertificateId, CertificateTable::ClientCertWithKey>
71
{
72
public:
73
    using Super = app::Storage::FabricTableImpl<CertificateId, CertificateTable::ClientCertWithKey>;
74
75
0
    ClientCertificateTable() : Super(kMaxClientCertificatesPerFabric, kMaxCertificatesPerEndpoint) {}
76
0
    ~ClientCertificateTable() { Finish(); };
77
};
78
79
class CertificateTableImpl : public CertificateTable
80
{
81
public:
82
0
    CertificateTableImpl() {}
83
0
    ~CertificateTableImpl() { Finish(); };
84
85
0
    bool IsInitialized() { return (mStorage != nullptr); }
86
87
    CHIP_ERROR Init(PersistentStorageDelegate & storage) override;
88
    void Finish() override;
89
90
    CHIP_ERROR SetEndpoint(EndpointId endpoint);
91
92
    // Data
93
    CHIP_ERROR UpsertRootCertificateEntry(FabricIndex fabric_index, Optional<TLSCAID> & id, RootBuffer & buffer,
94
                                          const ByteSpan & certificate) override;
95
    CHIP_ERROR GetRootCertificateEntry(FabricIndex fabric_index, TLSCAID id, BufferedRootCert & entry) override;
96
    CHIP_ERROR HasRootCertificateEntry(FabricIndex fabric_index, TLSCAID id) override;
97
    CHIP_ERROR IterateRootCertificates(FabricIndex fabric, BufferedRootCert & store, IterateRootCertFnType iterateFn) override;
98
    CHIP_ERROR RemoveRootCertificate(FabricIndex fabric, TLSCAID id) override;
99
    CHIP_ERROR GetRootCertificateCount(FabricIndex fabric, uint8_t & outCount) override;
100
101
    CHIP_ERROR PrepareClientCertificate(FabricIndex fabric, const ByteSpan & nonce, ClientBuffer & buffer, Optional<TLSCCDID> & id,
102
                                        MutableByteSpan & csr, MutableByteSpan & nonceSignature) override;
103
    CHIP_ERROR UpdateClientCertificateEntry(FabricIndex fabric_index, TLSCCDID id, ClientBuffer & buffer,
104
                                            const ClientCertStruct & entry) override;
105
    CHIP_ERROR GetClientCertificateEntry(FabricIndex fabric_index, TLSCCDID id, BufferedClientCert & entry) override;
106
    CHIP_ERROR HasClientCertificateEntry(FabricIndex fabric_index, TLSCCDID id) override;
107
    CHIP_ERROR IterateClientCertificates(FabricIndex fabric, BufferedClientCert & store,
108
                                         IterateClientCertFnType iterateFn) override;
109
    CHIP_ERROR RemoveClientCertificate(FabricIndex fabric, TLSCCDID id) override;
110
    CHIP_ERROR GetClientCertificateCount(FabricIndex fabric, uint8_t & outCount) override;
111
112
    CHIP_ERROR RemoveFabric(FabricIndex fabric) override;
113
114
private:
115
    CHIP_ERROR FindRootCertificateEntry(TLSCAID id, FabricIndex out_fabric);
116
    CHIP_ERROR FindClientCertificateEntry(TLSCCDID id, FabricIndex out_fabric);
117
118
    EndpointId mEndpointId = kInvalidEndpointId;
119
    RootCertificateTable mRootCertificates;
120
    ClientCertificateTable mClientCertificates;
121
    PersistentStorageDelegate * mStorage = nullptr;
122
};
123
124
} // namespace Tls
125
} // namespace Clusters
126
} // namespace app
127
} // namespace chip