-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathexample.cpp
More file actions
96 lines (78 loc) · 4.01 KB
/
example.cpp
File metadata and controls
96 lines (78 loc) · 4.01 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
// SPAKE2 Basic Example - Demonstrates simple password-authenticated key exchange
// Based on RFC 9382 implementation
#include "spake2/spake2.h"
#include "spake2/spake2_constants.h"
#include <iostream>
#include <vector>
#include <string>
#include <iomanip>
void printBytes(const std::string& label, const std::vector<uint8_t>& bytes) {
std::cout << label << ": ";
for (size_t i = 0; i < std::min(bytes.size(), size_t(8)); ++i) {
std::cout << std::hex << std::setfill('0') << std::setw(2)
<< static_cast<int>(bytes[i]);
}
if (bytes.size() > 8) {
std::cout << "... (" << bytes.size() << " bytes total)";
}
std::cout << std::dec << std::endl;
}
int main() {
std::cout << "SPAKE2 Basic Example - Password-Authenticated Key Exchange\n";
std::cout << "=========================================================\n\n";
try {
// Both parties use the same password
std::string password = "secure_password_123";
std::vector<uint8_t> passwordBytes(password.begin(), password.end());
std::cout << "Setting up SPAKE2 protocol with password: \"" << password << "\"\n\n";
// Create default options
auto options = spake2::DefaultOptions();
// Create client (party A) and server (party B)
auto client = spake2::SPAKE2::createClient(passwordBytes, options);
auto server = spake2::SPAKE2::createServer(passwordBytes, options);
std::cout << "=== Step 1: Client starts the protocol ===\n";
auto clientMessage = client->start();
printBytes("Client message (pA)", clientMessage);
std::cout << "Client sends message to server...\n\n";
std::cout << "=== Step 2: Server processes client message and responds ===\n";
auto serverMessage = server->exchange(clientMessage);
printBytes("Server message (pB)", serverMessage);
std::cout << "Server sends response to client...\n\n";
std::cout << "=== Step 3: Client finishes and generates confirmation ===\n";
auto clientConfirmation = client->finish(serverMessage);
printBytes("Client confirmation", clientConfirmation);
std::cout << "Client sends confirmation to server...\n\n";
std::cout << "=== Step 4: Server validates and generates confirmation ===\n";
auto serverConfirmation = server->confirm(clientConfirmation);
printBytes("Server confirmation", serverConfirmation);
std::cout << "Server sends confirmation to client...\n\n";
std::cout << "=== Step 5: Client verifies server confirmation ===\n";
client->verify(serverConfirmation);
std::cout << "✓ Client successfully verified server confirmation\n\n";
std::cout << "=== Step 6: Both parties derive shared key ===\n";
auto clientKey = client->getSharedKey();
auto serverKey = server->getSharedKey();
printBytes("Client shared key", clientKey);
printBytes("Server shared key", serverKey);
// Verify keys match
if (clientKey == serverKey) {
std::cout << "\n✓ SUCCESS: Both parties derived the same shared key!\n";
std::cout << "✓ SPAKE2 key exchange completed successfully\n";
std::cout << "✓ Shared key can now be used for secure communication\n";
} else {
std::cout << "\n✗ ERROR: Key mismatch - this should not happen!\n";
return 1;
}
} catch (const std::exception& e) {
std::cout << "\n✗ ERROR: " << e.what() << std::endl;
return 1;
}
std::cout << "\n=== Protocol Summary ===\n";
std::cout << "SPAKE2 provides:\n";
std::cout << "• Password-authenticated key exchange\n";
std::cout << "• Protection against offline dictionary attacks\n";
std::cout << "• Mutual authentication between parties\n";
std::cout << "• Forward secrecy with ephemeral keys\n";
std::cout << "• RFC 9382 compliance\n";
return 0;
}