1 /* Copyright (c) 2012-2016, The Tor Project, Inc. */
2 /* See LICENSE for licensing information */
8 #define ONION_NTOR_PRIVATE
13 #include "crypto_curve25519.h"
14 #include "onion_ntor.h"
16 #define N_ARGS(n) STMT_BEGIN { \
18 fprintf(stderr, "%s needs %d arguments.\n",argv[1],n); \
22 #define BASE16(idx, var, n) STMT_BEGIN { \
23 const char *s = argv[(idx)]; \
24 if (base16_decode((char*)var, n, s, strlen(s)) < 0 ) { \
25 fprintf(stderr, "couldn't decode argument %d (%s)\n",idx,s); \
29 #define INT(idx, var) STMT_BEGIN { \
30 var = atoi(argv[(idx)]); \
32 fprintf(stderr, "bad integer argument %d (%s)\n",idx,argv[(idx)]); \
37 client1(int argc
, char **argv
)
39 /* client1 nodeID B -> msg state */
40 curve25519_public_key_t B
;
41 uint8_t node_id
[DIGEST_LEN
];
42 ntor_handshake_state_t
*state
= NULL
;
43 uint8_t msg
[NTOR_ONIONSKIN_LEN
];
48 BASE16(2, node_id
, DIGEST_LEN
);
49 BASE16(3, B
.public_key
, CURVE25519_PUBKEY_LEN
);
51 if (onion_skin_ntor_create(node_id
, &B
, &state
, msg
)<0) {
52 fprintf(stderr
, "handshake failed");
56 base16_encode(buf
, sizeof(buf
), (const char*)msg
, sizeof(msg
));
58 base16_encode(buf
, sizeof(buf
), (void*)state
, sizeof(*state
));
61 ntor_handshake_state_free(state
);
66 server1(int argc
, char **argv
)
68 uint8_t msg_in
[NTOR_ONIONSKIN_LEN
];
69 curve25519_keypair_t kp
;
70 di_digest256_map_t
*keymap
=NULL
;
71 uint8_t node_id
[DIGEST_LEN
];
74 uint8_t msg_out
[NTOR_REPLY_LEN
];
81 /* server1: b nodeID msg N -> msg keys */
83 BASE16(2, kp
.seckey
.secret_key
, CURVE25519_SECKEY_LEN
);
84 BASE16(3, node_id
, DIGEST_LEN
);
85 BASE16(4, msg_in
, NTOR_ONIONSKIN_LEN
);
88 curve25519_public_key_generate(&kp
.pubkey
, &kp
.seckey
);
89 dimap_add_entry(&keymap
, kp
.pubkey
.public_key
, &kp
);
91 keys
= tor_malloc(keybytes
);
92 hexkeys
= tor_malloc(keybytes
*2+1);
93 if (onion_skin_ntor_server_handshake(
94 msg_in
, keymap
, NULL
, node_id
, msg_out
, keys
,
95 (size_t)keybytes
)<0) {
96 fprintf(stderr
, "handshake failed");
101 base16_encode(buf
, sizeof(buf
), (const char*)msg_out
, sizeof(msg_out
));
103 base16_encode(hexkeys
, keybytes
*2+1, (const char*)keys
, keybytes
);
104 printf("%s\n", hexkeys
);
109 dimap_free(keymap
, NULL
);
114 client2(int argc
, char **argv
)
116 struct ntor_handshake_state_t state
;
117 uint8_t msg
[NTOR_REPLY_LEN
];
124 BASE16(2, (&state
), sizeof(state
));
125 BASE16(3, msg
, sizeof(msg
));
128 keys
= tor_malloc(keybytes
);
129 hexkeys
= tor_malloc(keybytes
*2+1);
130 if (onion_skin_ntor_client_handshake(&state
, msg
, keys
, keybytes
, NULL
)<0) {
131 fprintf(stderr
, "handshake failed");
136 base16_encode(hexkeys
, keybytes
*2+1, (const char*)keys
, keybytes
);
137 printf("%s\n", hexkeys
);
146 main(int argc
, char **argv
)
149 client1: nodeID B -> msg state
150 server1: b nodeID msg N -> msg keys
151 client2: state msg N -> keys
154 fprintf(stderr
, "I need arguments. Read source for more info.\n");
156 } else if (!strcmp(argv
[1], "client1")) {
157 return client1(argc
, argv
);
158 } else if (!strcmp(argv
[1], "server1")) {
159 return server1(argc
, argv
);
160 } else if (!strcmp(argv
[1], "client2")) {
161 return client2(argc
, argv
);
163 fprintf(stderr
, "What's a %s?\n", argv
[1]);