Ring Daemon
Loading...
Searching...
No Matches
sdes_negotiator.cpp
Go to the documentation of this file.
1/*
2 * Copyright (C) 2004-2026 Savoir-faire Linux Inc.
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 3 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <https://www.gnu.org/licenses/>.
16 */
17
18#include "sdes_negotiator.h"
19#include "logger.h"
20
21#include <regex>
22
23#include <cstdio>
24
25namespace jami {
26
27std::vector<CryptoAttribute>
28SdesNegotiator::parse(const std::vector<std::string>& attributes)
29{
30 // The patterns below try to follow
31 // the ABNF grammar rules described in
32 // RFC4568 section 9.2 with the general
33 // syntax :
34 // a=crypto:tag 1*WSP crypto-suite 1*WSP key-params *(1*WSP session-param)
35
36 // used to match white space (which are used as separator)
37
38 static const std::regex generalSyntaxPattern {"[\x20\x09]+"};
39
40 static const std::regex tagPattern {"^([0-9]{1,9})"};
41
42 static const std::regex cryptoSuitePattern {"(AES_CM_128_HMAC_SHA1_80|"
43 "AES_CM_128_HMAC_SHA1_32|"
44 "F8_128_HMAC_SHA1_80|"
45 "[A-Za-z0-9_]+)"}; // srtp-crypto-suite-ext
46
47 static const std::regex keyParamsPattern {"(inline|[A-Za-z0-9_]+)\\:"
48 "([A-Za-z0-9\x2B\x2F\x3D]+)"
49 "((\\|2\\^)([0-9]+)\\|"
50 "([0-9]+)\\:"
51 "([0-9]{1,3})\\;?)?"};
52
53 // Take each line from the vector
54 // and parse its content
55
56 std::vector<CryptoAttribute> cryptoAttributeVector;
57
58 for (const auto& item : attributes) {
59 // Split the line into its component that we will analyze further down.
60 // Additional white space is added to better split the content
61 // Result is stored in the sdsLine
62
63 std::vector<std::string> sdesLine;
64 std::smatch sm_generalSyntaxPattern;
65
66 std::sregex_token_iterator iter(item.begin(), item.end(), generalSyntaxPattern, -1), end;
67 for (; iter != end; ++iter)
68 sdesLine.push_back(*iter);
69
70 if (sdesLine.size() < 3) {
71 throw ParseError("Missing components in SDES line");
72 }
73
74 // Check if the attribute starts with a=crypto
75 // and get the tag for this line
76
77 std::string tag;
78 std::smatch sm_tagPattern;
79
81 tag = sm_tagPattern[1];
82
83 } else {
84 throw ParseError("No Matching Found in Tag Attribute");
85 }
86
87 // Check if the crypto suite is valid and retrieve
88 // its value.
89
90 std::string cryptoSuite;
91 std::smatch sm_cryptoSuitePattern;
92
95
96 } else {
97 throw ParseError("No Matching Found in CryptoSuite Attribute");
98 }
99
100 // Parse one or more key-params field.
101 // Group number is used to locate different paras
102
103 std::string srtpKeyInfo;
104 std::string srtpKeyMethod;
105 std::string lifetime;
106 std::string mkiLength;
107 std::string mkiValue;
108 std::smatch sm_keyParamsPattern;
109
116
117 } else {
118 throw ParseError("No Matching Found in Key-params Attribute");
119 }
120
121 // Add the new CryptoAttribute to the vector
122 cryptoAttributeVector.emplace_back(std::move(tag),
123 std::move(cryptoSuite),
124 std::move(srtpKeyMethod),
125 std::move(srtpKeyInfo),
126 std::move(lifetime),
127 std::move(mkiValue),
128 std::move(mkiLength));
129 }
131}
132
133CryptoAttribute
134SdesNegotiator::negotiate(const std::vector<std::string>& attributes)
135{
136 try {
138 for (const auto& iter_offer : cryptoAttributeVector) {
139 for (const auto& iter_local : CryptoSuites) {
140 if (iter_offer.getCryptoSuite() == iter_local.name)
141 return iter_offer;
142 }
143 }
144 } catch (const ParseError& exception) {
145 JAMI_WARNING("");
146 }
147 return {};
148}
149
150} // namespace jami
General exception object that is thrown when an error occurred with a regular expression operation.
static CryptoAttribute negotiate(const std::vector< std::string > &attributes)
#define JAMI_WARNING(formatstr,...)
Definition logger.h:242
void emitSignal(Args... args)
Definition jami_signal.h:64
static std::vector< CryptoSuiteDefinition > CryptoSuites
List of accepted Crypto-Suites as defined in RFC4568 (6.2)
bool regex_search(string_view sv, svmatch &m, const regex &e, regex_constants::match_flag_type flags=regex_constants::match_default)