ndn-embeds 0.1.0
Lightweight NDN protocol stack for embedded systems
Loading...
Searching...
No Matches
certificate.cpp
Go to the documentation of this file.
1
6#include "ndn/certificate.hpp"
7
8#include "ndn/crypto.hpp"
9#include "ndn/tlv.hpp"
10
11#include <cstring>
12
13namespace ndn {
14
15// =============================================================================
16// ValidityPeriod implementation
17// =============================================================================
18
19namespace {
20
24void formatTimestamp(char* out, uint16_t year, uint8_t month, uint8_t day, uint8_t hour,
25 uint8_t minute, uint8_t second) {
26 // YYYYMMDDThhmmss
27 out[0] = '0' + (year / 1000) % 10;
28 out[1] = '0' + (year / 100) % 10;
29 out[2] = '0' + (year / 10) % 10;
30 out[3] = '0' + year % 10;
31 out[4] = '0' + month / 10;
32 out[5] = '0' + month % 10;
33 out[6] = '0' + day / 10;
34 out[7] = '0' + day % 10;
35 out[8] = 'T';
36 out[9] = '0' + hour / 10;
37 out[10] = '0' + hour % 10;
38 out[11] = '0' + minute / 10;
39 out[12] = '0' + minute % 10;
40 out[13] = '0' + second / 10;
41 out[14] = '0' + second % 10;
42}
43
47bool isValidTimestamp(std::string_view ts) {
48 if (ts.size() != VALIDITY_TIMESTAMP_SIZE) {
49 return false;
50 }
51 // Simple check: position of 'T' and digits
52 if (ts[8] != 'T') {
53 return false;
54 }
55 for (size_t i = 0; i < VALIDITY_TIMESTAMP_SIZE; ++i) {
56 if (i == 8) {
57 continue; // 'T'
58 }
59 if (ts[i] < '0' || ts[i] > '9') {
60 return false;
61 }
62 }
63 return true;
64}
65
70int compareTimestamp(const char* a, const char* b) {
71 return std::memcmp(a, b, VALIDITY_TIMESTAMP_SIZE);
72}
73
74} // namespace
75
77 std::string_view notAfter) {
79
80 if (!isValidTimestamp(notBefore) || !isValidTimestamp(notAfter)) {
81 return {.value = ValidityPeriod{}, .error = Error::InvalidParam};
82 }
83
84 std::memcpy(vp.notBefore_.data(), notBefore.data(), VALIDITY_TIMESTAMP_SIZE);
85 std::memcpy(vp.notAfter_.data(), notAfter.data(), VALIDITY_TIMESTAMP_SIZE);
86
87 return {.value = vp, .error = Error::Success};
88}
89
90Result<ValidityPeriod> ValidityPeriod::fromWire(const uint8_t* buf, size_t len, size_t* bytesRead) {
92 TlvDecoder decoder(buf, len);
93
94 // ValidityPeriod TLV header
95 auto header = decoder.readTlvHeader();
96 if (!header.ok()) {
97 return {.value = ValidityPeriod{}, .error = header.error};
98 }
99
100 if (header.value.type != tlv::ValidityPeriod) {
101 return {.value = ValidityPeriod{}, .error = Error::InvalidPacket};
102 }
103
104 const size_t vpEnd = decoder.position() + header.value.length;
105
106 // NotBefore
107 auto nbHeader = decoder.readTlvHeader();
108 if (!nbHeader.ok() || nbHeader.value.type != tlv::NotBefore) {
109 return {.value = ValidityPeriod{}, .error = Error::InvalidPacket};
110 }
111 if (nbHeader.value.length != VALIDITY_TIMESTAMP_SIZE) {
112 return {.value = ValidityPeriod{}, .error = Error::InvalidPacket};
113 }
114 Error err = decoder.readBytes(reinterpret_cast<uint8_t*>(vp.notBefore_.data()),
116 if (err != Error::Success) {
117 return {.value = ValidityPeriod{}, .error = err};
118 }
119
120 // NotAfter
121 auto naHeader = decoder.readTlvHeader();
122 if (!naHeader.ok() || naHeader.value.type != tlv::NotAfter) {
123 return {.value = ValidityPeriod{}, .error = Error::InvalidPacket};
124 }
125 if (naHeader.value.length != VALIDITY_TIMESTAMP_SIZE) {
126 return {.value = ValidityPeriod{}, .error = Error::InvalidPacket};
127 }
128 err =
129 decoder.readBytes(reinterpret_cast<uint8_t*>(vp.notAfter_.data()), VALIDITY_TIMESTAMP_SIZE);
130 if (err != Error::Success) {
131 return {.value = ValidityPeriod{}, .error = err};
132 }
133
134 if (decoder.position() != vpEnd) {
135 return {.value = ValidityPeriod{}, .error = Error::DecodeFailed};
136 }
137
138 if (bytesRead != nullptr) {
139 *bytesRead = decoder.position();
140 }
141
142 return {.value = vp, .error = Error::Success};
143}
144
145Error ValidityPeriod::encode(uint8_t* buf, size_t bufSize, size_t& encodedLen) const {
146 // Encode ValidityPeriod contents
147 uint8_t valueBuf[64];
148 TlvEncoder valueEncoder(valueBuf, sizeof(valueBuf));
149
150 // NotBefore
151 Error err =
152 valueEncoder.writeTlv(tlv::NotBefore, reinterpret_cast<const uint8_t*>(notBefore_.data()),
154 if (err != Error::Success) {
155 return err;
156 }
157
158 // NotAfter
159 err = valueEncoder.writeTlv(tlv::NotAfter, reinterpret_cast<const uint8_t*>(notAfter_.data()),
161 if (err != Error::Success) {
162 return err;
163 }
164
165 // ValidityPeriod TLV
166 TlvEncoder encoder(buf, bufSize);
167 err = encoder.writeTlv(tlv::ValidityPeriod, valueBuf, valueEncoder.size());
168 if (err != Error::Success) {
169 return err;
170 }
171
172 encodedLen = encoder.size();
173 return Error::Success;
174}
175
176Error ValidityPeriod::setNotBefore(uint16_t year, uint8_t month, uint8_t day, uint8_t hour,
177 uint8_t minute, uint8_t second) {
178 formatTimestamp(notBefore_.data(), year, month, day, hour, minute, second);
179 return Error::Success;
180}
181
182Error ValidityPeriod::setNotBefore(std::string_view timestamp) {
183 if (!isValidTimestamp(timestamp)) {
184 return Error::InvalidParam;
185 }
186 std::memcpy(notBefore_.data(), timestamp.data(), VALIDITY_TIMESTAMP_SIZE);
187 return Error::Success;
188}
189
190Error ValidityPeriod::setNotAfter(uint16_t year, uint8_t month, uint8_t day, uint8_t hour,
191 uint8_t minute, uint8_t second) {
192 formatTimestamp(notAfter_.data(), year, month, day, hour, minute, second);
193 return Error::Success;
194}
195
196Error ValidityPeriod::setNotAfter(std::string_view timestamp) {
197 if (!isValidTimestamp(timestamp)) {
198 return Error::InvalidParam;
199 }
200 std::memcpy(notAfter_.data(), timestamp.data(), VALIDITY_TIMESTAMP_SIZE);
201 return Error::Success;
202}
203
204bool ValidityPeriod::isValidAt(std::string_view currentTimestamp) const {
205 if (currentTimestamp.size() != VALIDITY_TIMESTAMP_SIZE) {
206 return false;
207 }
208 // notBefore <= current <= notAfter
209 return compareTimestamp(notBefore_.data(), currentTimestamp.data()) <= 0 &&
210 compareTimestamp(currentTimestamp.data(), notAfter_.data()) <= 0;
211}
212
213bool ValidityPeriod::equals(const ValidityPeriod& other) const {
214 return std::memcmp(notBefore_.data(), other.notBefore_.data(), VALIDITY_TIMESTAMP_SIZE) == 0 &&
215 std::memcmp(notAfter_.data(), other.notAfter_.data(), VALIDITY_TIMESTAMP_SIZE) == 0;
216}
217
218// =============================================================================
219// Certificate implementation
220// =============================================================================
221
223 Certificate cert;
224
225 // ContentType must be Key
226 if (data.contentType() != ContentType::Key) {
227 return {.value = Certificate{}, .error = Error::InvalidPacket};
228 }
229
230 // Parse name: /<IdentityName>/KEY/<KeyId>/<IssuerId>/<Version>
231 const Name& name = data.name();
232 if (name.componentCount() < 4) {
233 return {.value = Certificate{}, .error = Error::InvalidPacket};
234 }
235
236 // Find "KEY" component
237 size_t keyIndex = 0;
238 bool foundKey = false;
239 for (size_t i = 0; i < name.componentCount(); ++i) {
240 auto comp = name.component(i);
241 if (comp.size == 3 && std::memcmp(comp.value, "KEY", 3) == 0) {
242 keyIndex = i;
243 foundKey = true;
244 break;
245 }
246 }
247
248 if (!foundKey || keyIndex == 0 || name.componentCount() < keyIndex + 3) {
249 return {.value = Certificate{}, .error = Error::InvalidPacket};
250 }
251
252 // Identity name = components before "KEY"
253 // Build identity name
255 for (size_t i = 0; i < keyIndex; ++i) {
256 auto comp = name.component(i);
257 identityName.appendComponent(comp.value, comp.size);
258 }
259 cert.identityName_ = identityName;
260
261 // Key ID = component after "KEY"
262 auto keyIdComp = name.component(keyIndex + 1);
263 if (keyIdComp.size <= cert.keyId_.size()) {
264 std::memcpy(cert.keyId_.data(), keyIdComp.value, keyIdComp.size);
265 cert.keyIdSize_ = keyIdComp.size;
266 }
267
268 // Issuer ID = component after Key ID
269 auto issuerIdComp = name.component(keyIndex + 2);
270 if (issuerIdComp.size <= cert.issuerId_.size()) {
271 std::memcpy(cert.issuerId_.data(), issuerIdComp.value, issuerIdComp.size);
272 cert.issuerIdSize_ = issuerIdComp.size;
273 }
274
275 // Version = last component (if it's a version component, decode it)
276 if (name.componentCount() > keyIndex + 3) {
277 auto versionComp = name.component(keyIndex + 3);
278 // Simple version: just use the bytes as version number
279 uint64_t version = 0;
280 for (size_t i = 0; i < versionComp.size && i < 8; ++i) {
281 version = (version << 8) | versionComp.value[i];
282 }
283 cert.version_ = version;
284 }
285
286 // Public key = content
287 if (data.hasContent()) {
288 const size_t keySize = data.contentSize();
289 if (keySize > CERTIFICATE_MAX_KEY_SIZE) {
290 return {.value = Certificate{}, .error = Error::BufferTooSmall};
291 }
292 std::memcpy(cert.publicKey_.data(), data.content(), keySize);
293 cert.publicKeySize_ = keySize;
294 }
295
296 // Signature info
297 cert.signatureType_ = data.signatureType();
298 if (data.hasSignature()) {
299 const size_t sigSize = data.signatureValueSize();
300 if (sigSize <= SIGNATURE_MAX_SIZE) {
301 std::memcpy(cert.signatureValue_.data(), data.signatureValue(), sigSize);
302 cert.signatureSize_ = sigSize;
303 }
304 }
305
306 return {.value = cert, .error = Error::Success};
307}
308
309Result<Certificate> Certificate::fromWire(const uint8_t* buf, size_t len) {
310 // First decode as Data
311 auto dataResult = Data::fromWire(buf, len);
312 if (!dataResult.ok()) {
313 return {.value = Certificate{}, .error = dataResult.error};
314 }
315
316 return fromData(dataResult.value);
317}
318
320 // Build certificate name
321 Name certName;
322 Error err = buildName(certName);
323 if (err != Error::Success) {
324 return err;
325 }
326
327 data.setName(certName);
328 data.setContentType(ContentType::Key);
329
330 // Set public key as content
331 if (publicKeySize_ > 0) {
332 err = data.setContent(publicKey_.data(), publicKeySize_);
333 if (err != Error::Success) {
334 return err;
335 }
336 }
337
338 // Set freshness period (recommended ~1 hour)
339 data.setFreshnessPeriod(3600000);
340
341 // Copy signature info
342 data.setSignatureType(signatureType_);
343
344 return Error::Success;
345}
346
347Error Certificate::encode(uint8_t* buf, size_t bufSize, size_t& encodedLen) const {
348 uint8_t valueBuf[PACKET_MAX_SIZE];
349
350 // Encode signed portion (Name + MetaInfo + Content + SignatureInfo)
351 size_t signedLen = 0;
352 Error err = encodeSignedPortion(valueBuf, sizeof(valueBuf), signedLen);
353 if (err != Error::Success) {
354 return err;
355 }
356
357 TlvEncoder valueEncoder(valueBuf + signedLen, sizeof(valueBuf) - signedLen);
358
359 // SignatureValue
360 err = valueEncoder.writeTlv(tlv::SignatureValue, signatureValue_.data(), signatureSize_);
361 if (err != Error::Success) {
362 return err;
363 }
364
365 // Data TLV header
366 const size_t valueLen = signedLen + valueEncoder.size();
367 const size_t headerSize = varNumberSize(tlv::Data) + varNumberSize(valueLen);
368 const size_t totalSize = headerSize + valueLen;
369
370 if (bufSize < totalSize) {
371 return Error::BufferTooSmall;
372 }
373
374 TlvEncoder encoder(buf, bufSize);
375 err = encoder.writeType(tlv::Data);
376 if (err != Error::Success) {
377 return err;
378 }
379
380 err = encoder.writeLength(valueLen);
381 if (err != Error::Success) {
382 return err;
383 }
384
385 err = encoder.writeBytes(valueBuf, valueLen);
386 if (err != Error::Success) {
387 return err;
388 }
389
390 encodedLen = encoder.size();
391 return Error::Success;
392}
393
395 identityName_ = name;
396 return *this;
397}
398
399Error Certificate::setIdentityName(std::string_view uri) {
400 auto result = Name::fromUri(uri);
401 if (!result.ok()) {
402 return result.error;
403 }
404 identityName_ = result.value;
405 return Error::Success;
406}
407
408Error Certificate::setKeyId(const uint8_t* id, size_t len) {
409 if (len > keyId_.size()) {
410 return Error::BufferTooSmall;
411 }
412 std::memcpy(keyId_.data(), id, len);
413 keyIdSize_ = len;
414 return Error::Success;
415}
416
417Error Certificate::setIssuerId(const uint8_t* id, size_t len) {
418 if (len > issuerId_.size()) {
419 return Error::BufferTooSmall;
420 }
421 std::memcpy(issuerId_.data(), id, len);
422 issuerIdSize_ = len;
423 return Error::Success;
424}
425
426Error Certificate::setIssuerId(std::string_view id) {
427 return setIssuerId(reinterpret_cast<const uint8_t*>(id.data()), id.size());
428}
429
431 version_ = version;
432 return *this;
433}
434
435Error Certificate::setPublicKey(const uint8_t* key, size_t len) {
436 if (len > CERTIFICATE_MAX_KEY_SIZE) {
437 return Error::BufferTooSmall;
438 }
439 std::memcpy(publicKey_.data(), key, len);
440 publicKeySize_ = len;
441 return Error::Success;
442}
443
445 validity_ = validity;
446 return *this;
447}
448
450 signatureType_ = type;
451 return *this;
452}
453
455 name = Name();
456
457 // Copy identity name components
458 for (size_t i = 0; i < identityName_.componentCount(); ++i) {
459 auto comp = identityName_.component(i);
460 const Error err = name.appendComponent(comp.value, comp.size);
461 if (err != Error::Success) {
462 return err;
463 }
464 }
465
466 // "KEY" component
467 Error err = name.appendComponent(reinterpret_cast<const uint8_t*>("KEY"), 3);
468 if (err != Error::Success) {
469 return err;
470 }
471
472 // Key ID component
473 if (keyIdSize_ > 0) {
474 err = name.appendComponent(keyId_.data(), keyIdSize_);
475 if (err != Error::Success) {
476 return err;
477 }
478 }
479
480 // Issuer ID component
481 if (issuerIdSize_ > 0) {
482 err = name.appendComponent(issuerId_.data(), issuerIdSize_);
483 if (err != Error::Success) {
484 return err;
485 }
486 }
487
488 // Version component (encode as big-endian bytes)
489 if (version_ > 0) {
490 uint8_t versionBytes[8];
491 size_t versionLen = 0;
492 uint64_t v = version_;
493
494 // Calculate number of bytes needed
495 if (v <= 0xFF) {
496 versionLen = 1;
497 } else if (v <= 0xFFFF) {
498 versionLen = 2;
499 } else if (v <= 0xFFFFFF) {
500 versionLen = 3;
501 } else if (v <= 0xFFFFFFFF) {
502 versionLen = 4;
503 } else {
504 versionLen = 8;
505 }
506
507 // Encode big-endian
508 for (size_t i = 0; i < versionLen; ++i) {
509 versionBytes[versionLen - 1 - i] = static_cast<uint8_t>(v & 0xFF);
510 v >>= 8;
511 }
512
513 err = name.appendComponent(versionBytes, versionLen);
514 if (err != Error::Success) {
515 return err;
516 }
517 }
518
519 return Error::Success;
520}
521
522Error Certificate::encodeSignedPortion(uint8_t* buf, size_t bufSize, size_t& encodedLen) const {
523 // Build certificate name
524 Name certName;
525 Error err = buildName(certName);
526 if (err != Error::Success) {
527 return err;
528 }
529
530 TlvEncoder encoder(buf, bufSize);
531
532 // Name
533 size_t nameLen = 0;
534 err = certName.encode(encoder.current(), encoder.remaining(), nameLen);
535 if (err != Error::Success) {
536 return err;
537 }
538 encoder.setPosition(encoder.position() + nameLen);
539
540 // MetaInfo (ContentType=Key, FreshnessPeriod=1 hour)
541 {
542 uint8_t metaBuf[24];
543 TlvEncoder metaEncoder(metaBuf, sizeof(metaBuf));
544 metaEncoder.writeTlvNonNegativeInteger(tlv::ContentType,
545 static_cast<uint8_t>(ContentType::Key));
546 metaEncoder.writeTlvNonNegativeInteger(tlv::FreshnessPeriod, 3600000);
547 encoder.writeTlv(tlv::MetaInfo, metaBuf, metaEncoder.size());
548 }
549
550 // Content (public key)
551 if (publicKeySize_ > 0) {
552 encoder.writeTlv(tlv::Content, publicKey_.data(), publicKeySize_);
553 }
554
555 // SignatureInfo (SignatureType + ValidityPeriod)
556 {
557 uint8_t sigInfoBuf[96];
558 TlvEncoder sigInfoEncoder(sigInfoBuf, sizeof(sigInfoBuf));
559 sigInfoEncoder.writeTlvNonNegativeInteger(tlv::SignatureType,
560 static_cast<uint8_t>(signatureType_));
561
562 size_t vpLen = 0;
563 uint8_t vpBuf[64];
564 validity_.encode(vpBuf, sizeof(vpBuf), vpLen);
565 sigInfoEncoder.writeBytes(vpBuf, vpLen);
566
567 encoder.writeTlv(tlv::SignatureInfo, sigInfoBuf, sigInfoEncoder.size());
568 }
569
570 encodedLen = encoder.size();
571 return Error::Success;
572}
573
575 signatureType_ = SignatureType::DigestSha256;
576
577 uint8_t signedBuf[PACKET_MAX_SIZE];
578 size_t signedLen = 0;
579 Error err = encodeSignedPortion(signedBuf, sizeof(signedBuf), signedLen);
580 if (err != Error::Success) {
581 return err;
582 }
583
584 err = crypto::sha256(signedBuf, signedLen, signatureValue_.data());
585 if (err != Error::Success) {
586 return err;
587 }
588
589 signatureSize_ = SHA256_DIGEST_SIZE;
590 return Error::Success;
591}
592
593Error Certificate::signWithHmac(const uint8_t* key, size_t keyLen) {
594 if (key == nullptr || keyLen == 0) {
595 return Error::InvalidParam;
596 }
597
598 signatureType_ = SignatureType::SignatureHmacWithSha256;
599
600 uint8_t signedBuf[PACKET_MAX_SIZE];
601 size_t signedLen = 0;
602 Error err = encodeSignedPortion(signedBuf, sizeof(signedBuf), signedLen);
603 if (err != Error::Success) {
604 return err;
605 }
606
607 err = crypto::hmacSha256(key, keyLen, signedBuf, signedLen, signatureValue_.data());
608 if (err != Error::Success) {
609 return err;
610 }
611
612 signatureSize_ = HMAC_SHA256_SIZE;
613 return Error::Success;
614}
615
617 if (signatureType_ != SignatureType::DigestSha256) {
618 return false;
619 }
620 if (signatureSize_ != SHA256_DIGEST_SIZE) {
621 return false;
622 }
623
624 uint8_t signedBuf[PACKET_MAX_SIZE];
625 size_t signedLen = 0;
626 if (encodeSignedPortion(signedBuf, sizeof(signedBuf), signedLen) != Error::Success) {
627 return false;
628 }
629
630 uint8_t computed[SHA256_DIGEST_SIZE];
631 if (crypto::sha256(signedBuf, signedLen, computed) != Error::Success) {
632 return false;
633 }
634
635 return crypto::constantTimeCompare(computed, signatureValue_.data(), SHA256_DIGEST_SIZE);
636}
637
638bool Certificate::verifyHmac(const uint8_t* key, size_t keyLen) const {
639 if (key == nullptr || keyLen == 0) {
640 return false;
641 }
642 if (signatureType_ != SignatureType::SignatureHmacWithSha256) {
643 return false;
644 }
645 if (signatureSize_ != HMAC_SHA256_SIZE) {
646 return false;
647 }
648
649 uint8_t signedBuf[PACKET_MAX_SIZE];
650 size_t signedLen = 0;
651 if (encodeSignedPortion(signedBuf, sizeof(signedBuf), signedLen) != Error::Success) {
652 return false;
653 }
654
655 uint8_t computed[HMAC_SHA256_SIZE];
656 if (crypto::hmacSha256(key, keyLen, signedBuf, signedLen, computed) != Error::Success) {
657 return false;
658 }
659
660 return crypto::constantTimeCompare(computed, signatureValue_.data(), HMAC_SHA256_SIZE);
661}
662
663bool Certificate::isValidAt(std::string_view timestamp) const {
664 return validity_.isValidAt(timestamp);
665}
666
667} // namespace ndn
NDN Certificate.
constexpr size_t CERTIFICATE_MAX_KEY_SIZE
Maximum public key size (DER-encoded SubjectPublicKeyInfo)
constexpr size_t VALIDITY_TIMESTAMP_SIZE
Length of ValidityPeriod ISO 8601 format string (YYYYMMDDThhmmss)
NDN Certificate.
Certificate & setVersion(uint64_t version)
Set the version.
bool isValidAt(std::string_view timestamp) const
Check if the certificate is valid at a given time.
Error setIssuerId(const uint8_t *id, size_t len)
Set the Issuer ID (bytes)
Error signWithDigestSha256()
Sign with DigestSha256.
Error toData(Data &data) const
Convert the Certificate to a Data packet.
static Result< Certificate > fromWire(const uint8_t *buf, size_t len)
Decode a Certificate from TLV wire format.
Certificate & setSignatureType(SignatureType type)
Set the signature type.
Error signWithHmac(const uint8_t *key, size_t keyLen)
Sign with HMAC-SHA256.
Certificate & setValidity(const ValidityPeriod &validity)
Set the validity period.
bool verifyHmac(const uint8_t *key, size_t keyLen) const
Verify an HMAC-SHA256 signature.
Error setKeyId(const uint8_t *id, size_t len)
Set the Key ID.
Certificate & setIdentityName(const Name &name)
Set the identity name.
Error encode(uint8_t *buf, size_t bufSize, size_t &encodedLen) const
Encode the Certificate to TLV wire format.
const Name & identityName() const
Get the identity name.
Error buildName(Name &name) const
Build the full certificate name and store it in a Name.
bool verifyDigestSha256() const
Verify a DigestSha256 signature.
Error setPublicKey(const uint8_t *key, size_t len)
Set the public key.
static Result< Certificate > fromData(const Data &data)
Create a Certificate from a Data packet.
const ValidityPeriod & validity() const
Get the validity period (const)
uint64_t version() const
Get the version.
NDN Data packet.
Definition data.hpp:49
Data & setFreshnessPeriod(uint32_t periodMs)
Set the FreshnessPeriod.
Definition data.cpp:39
const Name & name() const
Get the Name (const reference)
Definition data.hpp:104
bool hasContent() const
Check if content is set.
Definition data.hpp:147
size_t contentSize() const
Get the content size.
Definition data.hpp:141
Data & setContentType(ContentType type)
Set the content type.
Definition data.cpp:54
const uint8_t * content() const
Get a pointer to the content data.
Definition data.hpp:135
const uint8_t * signatureValue() const
Get a pointer to the signature value.
Definition data.hpp:302
Error setContent(const uint8_t *data, size_t size)
Set binary data as content.
Definition data.cpp:26
Data & setSignatureType(SignatureType type)
Set the signature type.
Definition data.cpp:59
size_t signatureValueSize() const
Get the size of the signature value.
Definition data.hpp:308
SignatureType signatureType() const
Get the signature type.
Definition data.hpp:260
ContentType contentType() const
Get the content type.
Definition data.hpp:177
bool hasSignature() const
Check if a signature is set.
Definition data.hpp:314
static Result< Data > fromWire(const uint8_t *buf, size_t len)
Decode a Data packet from TLV wire format.
Definition data.cpp:362
Data & setName(const Name &name)
Set the Name (supports method chaining)
Definition data.cpp:12
NDN Name class.
Definition name.hpp:64
Error encode(uint8_t *buf, size_t bufSize, size_t &encodedLen) const
Encode the Name to TLV wire format.
Definition name.cpp:186
Error appendComponent(std::string_view comp)
Append a string component.
Definition name.cpp:228
size_t componentCount() const
Get the number of components.
Definition name.hpp:133
NameComponent component(size_t index) const
Get the component at a given index.
Definition name.cpp:219
static Result< Name > fromUri(std::string_view uri)
Create a Name from a URI string.
Definition name.cpp:25
TLV decoder.
Definition tlv.hpp:235
size_t position() const
Get current position.
Definition tlv.hpp:320
Error readBytes(uint8_t *out, size_t len)
Read a specified number of bytes.
Definition tlv.cpp:239
Result< TlvHeader > readTlvHeader()
Read a TLV header (Type and Length) at once.
Definition tlv.cpp:224
TLV encoder.
Definition tlv.hpp:116
Error writeLength(size_t length)
Write a TLV Length.
Definition tlv.cpp:91
Error writeTlv(uint32_t type, const uint8_t *value, size_t valueLen)
Write a complete TLV structure.
Definition tlv.cpp:104
Error writeBytes(const uint8_t *data, size_t len)
Write a byte sequence.
Definition tlv.cpp:95
size_t size() const
Current write position (= number of bytes written)
Definition tlv.hpp:189
Error writeType(uint32_t type)
Write a TLV Type.
Definition tlv.cpp:87
Validity period.
static Result< ValidityPeriod > fromWire(const uint8_t *buf, size_t len, size_t *bytesRead=nullptr)
Decode a ValidityPeriod from TLV wire format.
const char * notAfter() const
Get the NotAfter time as an ISO 8601 string.
Error setNotAfter(uint16_t year, uint8_t month, uint8_t day, uint8_t hour, uint8_t minute, uint8_t second)
Set the NotAfter time from date/time components.
bool equals(const ValidityPeriod &other) const
Check equality of two validity periods.
static Result< ValidityPeriod > fromStrings(std::string_view notBefore, std::string_view notAfter)
Create a ValidityPeriod from ISO 8601 format strings.
Error setNotBefore(uint16_t year, uint8_t month, uint8_t day, uint8_t hour, uint8_t minute, uint8_t second)
Set the NotBefore time from date/time components.
bool isValidAt(std::string_view currentTimestamp) const
Check if the current time is within the validity period.
Error encode(uint8_t *buf, size_t bufSize, size_t &encodedLen) const
Encode the ValidityPeriod to TLV wire format.
const char * notBefore() const
Get the NotBefore time as an ISO 8601 string.
constexpr size_t PACKET_MAX_SIZE
Maximum packet size (ESP-NOW v2.0 compatible)
Definition common.hpp:122
Error
Error codes.
Definition common.hpp:24
NDN cryptographic utilities.
constexpr uint32_t MetaInfo
Meta information.
Definition tlv.hpp:60
constexpr uint32_t SignatureInfo
Signature info.
Definition tlv.hpp:62
constexpr uint32_t ValidityPeriod
Validity period (253)
Definition tlv.hpp:95
constexpr uint32_t NotBefore
Not before (254)
Definition tlv.hpp:96
constexpr uint32_t FreshnessPeriod
Freshness period.
Definition tlv.hpp:70
constexpr uint32_t Content
Content.
Definition tlv.hpp:61
constexpr uint32_t SignatureValue
Signature value.
Definition tlv.hpp:63
constexpr uint32_t ContentType
Content type.
Definition tlv.hpp:69
constexpr uint32_t Data
Data packet.
Definition tlv.hpp:28
constexpr uint32_t SignatureType
Signature type.
Definition tlv.hpp:77
constexpr uint32_t NotAfter
Not after (255)
Definition tlv.hpp:97
constexpr size_t SIGNATURE_MAX_SIZE
Maximum signature size (for ECDSA P-256, embedded)
Definition signature.hpp:38
constexpr size_t HMAC_SHA256_SIZE
HMAC-SHA256 size (bytes)
Definition signature.hpp:34
SignatureType
Signature type.
Definition signature.hpp:22
constexpr size_t SHA256_DIGEST_SIZE
SHA-256 digest size (bytes)
Definition signature.hpp:33
const uint8_t * value
Pointer to the component value.
Definition name.hpp:27
Result type template.
Definition common.hpp:147
NDN TLV (Type-Length-Value) encoding.
constexpr size_t varNumberSize(uint64_t value)
Calculate the encoded size of a VAR-NUMBER.
Definition tlv.hpp:339