stdex
Additional custom or not Standard C++ covered algorithms
Loading...
Searching...
No Matches
minisign.hpp
1/*
2 SPDX-License-Identifier: MIT
3 Copyright © 2023-2024 Amebis
4*/
5
6#pragma once
7
8#include "base64.hpp"
9#include "compat.hpp"
10#include "parser.hpp"
11#include "stream.hpp"
12#include <stdint.h>
13#include <string>
14#include <vector>
15
16namespace stdex
17{
18 namespace minisign
19 {
24 {
25 protected:
26 virtual bool do_match(
27 _In_reads_or_z_opt_(end) const char* text,
28 _In_ size_t start = 0,
29 _In_ size_t end = SIZE_MAX,
30 _In_ int flags = stdex::parser::match_default)
31 {
32 _Unreferenced_(flags);
33 _Assume_(text || start + 17 >= end);
34 if (start + 17 < end &&
35 text[start + 0] == 'u' &&
36 text[start + 1] == 'n' &&
37 text[start + 2] == 't' &&
38 text[start + 3] == 'r' &&
39 text[start + 4] == 'u' &&
40 text[start + 5] == 's' &&
41 text[start + 6] == 't' &&
42 text[start + 7] == 'e' &&
43 text[start + 8] == 'd' &&
44 text[start + 9] == ' ' &&
45 text[start + 10] == 'c' &&
46 text[start + 11] == 'o' &&
47 text[start + 12] == 'm' &&
48 text[start + 13] == 'm' &&
49 text[start + 14] == 'e' &&
50 text[start + 15] == 'n' &&
51 text[start + 16] == 't' &&
52 text[start + 17] == ':')
53 {
54 this->interval.end = (this->interval.start = start) + 18;
55 return true;
56 }
57 this->interval.invalidate();
58 return false;
59 }
60 };
61
66 {
67 protected:
68 virtual bool do_match(
69 _In_reads_or_z_opt_(end) const char* text,
70 _In_ size_t start = 0,
71 _In_ size_t end = SIZE_MAX,
72 _In_ int flags = stdex::parser::match_default)
73 {
74 _Unreferenced_(flags);
75 _Assume_(text || start + 1 >= end);
76 if (start + 1 < end &&
77 text[start + 0] == '\r' &&
78 text[start + 1] == '\n')
79 {
80 this->interval.end = (this->interval.start = start) + 2;
81 return true;
82 }
83 _Assume_(text || start >= end);
84 if (start < end && text[start] == '\n') {
85 this->interval.end = (this->interval.start = start) + 1;
86 return true;
87 }
88 this->interval.invalidate();
89 return false;
90 }
91 };
92
101 inline void parse_minisig(_Inout_ stdex::stream::basic& minisig, _Out_ uint8_t& algorithm, _Out_writes_all_(8) uint8_t key_id[8], _Out_writes_all_(64) uint8_t signature[64])
102 {
103 std::vector<uint8_t> data;
105 std::string line;
106 for (;;) {
107 minisig.readln(line);
108 if (!minisig.ok())
109 break;
110 if (line.empty() ||
111 untrusted_comment.match(line.data(), 0, line.size()))
112 continue;
113 stdex::base64_dec decoder; bool is_last;
114 decoder.decode(data, is_last, line.data(), line.size());
115 break;
116 }
117 if (data.size() < 74)
118 throw std::runtime_error("Minisign signature is too short");
119 if (data[0] != 'E')
120 throw std::runtime_error("not a Minisign signature");
121 algorithm = data[1];
122 memcpy(&key_id[0], &data[2], 8);
123 memcpy(&signature[0], &data[10], 64);
124 }
125 }
126}
Base64 decoding session.
Definition base64.hpp:274
void decode(std::vector< T_to, AX > &out, bool &is_last, const T_from *data, size_t size)
Decodes one block of information, and appends it to the output.
Definition base64.hpp:296
Test for CRLF or LF.
Definition minisign.hpp:66
Test for "untrusted comment:".
Definition minisign.hpp:24
‍UTF-8 byte-order-mark
Definition stream.hpp:84
Numerical interval.
Definition interval.hpp:18
T end
interval end
Definition interval.hpp:20
void invalidate()
Invalidates interval.
Definition interval.hpp:59
T start
interval start
Definition interval.hpp:19