control_auth.c 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441
  1. /* Copyright (c) 2004-2006, Roger Dingledine, Nick Mathewson.
  2. * Copyright (c) 2007-2019, The Tor Project, Inc. */
  3. /* See LICENSE for licensing information */
  4. /**
  5. * \file control_auth.c
  6. * \brief Authentication for Tor's control-socket interface.
  7. **/
  8. #include "core/or/or.h"
  9. #include "app/config/config.h"
  10. #include "core/mainloop/connection.h"
  11. #include "feature/control/control.h"
  12. #include "feature/control/control_cmd.h"
  13. #include "feature/control/control_auth.h"
  14. #include "feature/control/control_cmd_args_st.h"
  15. #include "feature/control/control_connection_st.h"
  16. #include "feature/control/control_proto.h"
  17. #include "lib/crypt_ops/crypto_rand.h"
  18. #include "lib/crypt_ops/crypto_util.h"
  19. #include "lib/encoding/confline.h"
  20. #include "lib/encoding/kvline.h"
  21. #include "lib/encoding/qstring.h"
  22. #include "lib/crypt_ops/crypto_s2k.h"
  23. /** If we're using cookie-type authentication, how long should our cookies be?
  24. */
  25. #define AUTHENTICATION_COOKIE_LEN 32
  26. /** If true, we've set authentication_cookie to a secret code and
  27. * stored it to disk. */
  28. static int authentication_cookie_is_set = 0;
  29. /** If authentication_cookie_is_set, a secret cookie that we've stored to disk
  30. * and which we're using to authenticate controllers. (If the controller can
  31. * read it off disk, it has permission to connect.) */
  32. static uint8_t *authentication_cookie = NULL;
  33. #define SAFECOOKIE_SERVER_TO_CONTROLLER_CONSTANT \
  34. "Tor safe cookie authentication server-to-controller hash"
  35. #define SAFECOOKIE_CONTROLLER_TO_SERVER_CONSTANT \
  36. "Tor safe cookie authentication controller-to-server hash"
  37. #define SAFECOOKIE_SERVER_NONCE_LEN DIGEST256_LEN
  38. /** Helper: Return a newly allocated string containing a path to the
  39. * file where we store our authentication cookie. */
  40. char *
  41. get_controller_cookie_file_name(void)
  42. {
  43. const or_options_t *options = get_options();
  44. if (options->CookieAuthFile && strlen(options->CookieAuthFile)) {
  45. return tor_strdup(options->CookieAuthFile);
  46. } else {
  47. return get_datadir_fname("control_auth_cookie");
  48. }
  49. }
  50. /* Initialize the cookie-based authentication system of the
  51. * ControlPort. If <b>enabled</b> is 0, then disable the cookie
  52. * authentication system. */
  53. int
  54. init_control_cookie_authentication(int enabled)
  55. {
  56. char *fname = NULL;
  57. int retval;
  58. if (!enabled) {
  59. authentication_cookie_is_set = 0;
  60. return 0;
  61. }
  62. fname = get_controller_cookie_file_name();
  63. retval = init_cookie_authentication(fname, "", /* no header */
  64. AUTHENTICATION_COOKIE_LEN,
  65. get_options()->CookieAuthFileGroupReadable,
  66. &authentication_cookie,
  67. &authentication_cookie_is_set);
  68. tor_free(fname);
  69. return retval;
  70. }
  71. /** Decode the hashed, base64'd passwords stored in <b>passwords</b>.
  72. * Return a smartlist of acceptable passwords (unterminated strings of
  73. * length S2K_RFC2440_SPECIFIER_LEN+DIGEST_LEN) on success, or NULL on
  74. * failure.
  75. */
  76. smartlist_t *
  77. decode_hashed_passwords(config_line_t *passwords)
  78. {
  79. char decoded[64];
  80. config_line_t *cl;
  81. smartlist_t *sl = smartlist_new();
  82. tor_assert(passwords);
  83. for (cl = passwords; cl; cl = cl->next) {
  84. const char *hashed = cl->value;
  85. if (!strcmpstart(hashed, "16:")) {
  86. if (base16_decode(decoded, sizeof(decoded), hashed+3, strlen(hashed+3))
  87. != S2K_RFC2440_SPECIFIER_LEN + DIGEST_LEN
  88. || strlen(hashed+3) != (S2K_RFC2440_SPECIFIER_LEN+DIGEST_LEN)*2) {
  89. goto err;
  90. }
  91. } else {
  92. if (base64_decode(decoded, sizeof(decoded), hashed, strlen(hashed))
  93. != S2K_RFC2440_SPECIFIER_LEN+DIGEST_LEN) {
  94. goto err;
  95. }
  96. }
  97. smartlist_add(sl,
  98. tor_memdup(decoded, S2K_RFC2440_SPECIFIER_LEN+DIGEST_LEN));
  99. }
  100. return sl;
  101. err:
  102. SMARTLIST_FOREACH(sl, char*, cp, tor_free(cp));
  103. smartlist_free(sl);
  104. return NULL;
  105. }
  106. const control_cmd_syntax_t authchallenge_syntax = {
  107. .min_args = 1,
  108. .max_args = 1,
  109. .accept_keywords=true,
  110. .kvline_flags=KV_OMIT_KEYS|KV_QUOTED_QSTRING,
  111. .store_raw_body=true
  112. };
  113. /** Called when we get an AUTHCHALLENGE command. */
  114. int
  115. handle_control_authchallenge(control_connection_t *conn,
  116. const control_cmd_args_t *args)
  117. {
  118. char *client_nonce;
  119. size_t client_nonce_len;
  120. char server_hash[DIGEST256_LEN];
  121. char server_hash_encoded[HEX_DIGEST256_LEN+1];
  122. char server_nonce[SAFECOOKIE_SERVER_NONCE_LEN];
  123. char server_nonce_encoded[(2*SAFECOOKIE_SERVER_NONCE_LEN) + 1];
  124. if (strcasecmp(smartlist_get(args->args, 0), "SAFECOOKIE")) {
  125. control_write_endreply(conn, 513,
  126. "AUTHCHALLENGE only supports SAFECOOKIE "
  127. "authentication");
  128. goto fail;
  129. }
  130. if (!authentication_cookie_is_set) {
  131. control_write_endreply(conn, 515, "Cookie authentication is disabled");
  132. goto fail;
  133. }
  134. if (args->kwargs == NULL || args->kwargs->next != NULL) {
  135. control_write_endreply(conn, 512,
  136. "Wrong number of arguments for AUTHCHALLENGE");
  137. goto fail;
  138. }
  139. if (strcmp(args->kwargs->key, "")) {
  140. control_write_endreply(conn, 512,
  141. "AUTHCHALLENGE does not accept keyword "
  142. "arguments.");
  143. goto fail;
  144. }
  145. bool contains_quote = strchr(args->raw_body, '\"');
  146. if (contains_quote) {
  147. /* The nonce was quoted */
  148. client_nonce = tor_strdup(args->kwargs->value);
  149. client_nonce_len = strlen(client_nonce);
  150. } else {
  151. /* The nonce was should be in hex. */
  152. const char *hex_nonce = args->kwargs->value;
  153. client_nonce_len = strlen(hex_nonce) / 2;
  154. client_nonce = tor_malloc(client_nonce_len);
  155. if (base16_decode(client_nonce, client_nonce_len, hex_nonce,
  156. strlen(hex_nonce)) != (int)client_nonce_len) {
  157. control_write_endreply(conn, 513, "Invalid base16 client nonce");
  158. tor_free(client_nonce);
  159. goto fail;
  160. }
  161. }
  162. crypto_rand(server_nonce, SAFECOOKIE_SERVER_NONCE_LEN);
  163. /* Now compute and send the server-to-controller response, and the
  164. * server's nonce. */
  165. tor_assert(authentication_cookie != NULL);
  166. {
  167. size_t tmp_len = (AUTHENTICATION_COOKIE_LEN +
  168. client_nonce_len +
  169. SAFECOOKIE_SERVER_NONCE_LEN);
  170. char *tmp = tor_malloc_zero(tmp_len);
  171. char *client_hash = tor_malloc_zero(DIGEST256_LEN);
  172. memcpy(tmp, authentication_cookie, AUTHENTICATION_COOKIE_LEN);
  173. memcpy(tmp + AUTHENTICATION_COOKIE_LEN, client_nonce, client_nonce_len);
  174. memcpy(tmp + AUTHENTICATION_COOKIE_LEN + client_nonce_len,
  175. server_nonce, SAFECOOKIE_SERVER_NONCE_LEN);
  176. crypto_hmac_sha256(server_hash,
  177. SAFECOOKIE_SERVER_TO_CONTROLLER_CONSTANT,
  178. strlen(SAFECOOKIE_SERVER_TO_CONTROLLER_CONSTANT),
  179. tmp,
  180. tmp_len);
  181. crypto_hmac_sha256(client_hash,
  182. SAFECOOKIE_CONTROLLER_TO_SERVER_CONSTANT,
  183. strlen(SAFECOOKIE_CONTROLLER_TO_SERVER_CONSTANT),
  184. tmp,
  185. tmp_len);
  186. conn->safecookie_client_hash = client_hash;
  187. tor_free(tmp);
  188. }
  189. base16_encode(server_hash_encoded, sizeof(server_hash_encoded),
  190. server_hash, sizeof(server_hash));
  191. base16_encode(server_nonce_encoded, sizeof(server_nonce_encoded),
  192. server_nonce, sizeof(server_nonce));
  193. control_printf_endreply(conn, 250,
  194. "AUTHCHALLENGE SERVERHASH=%s SERVERNONCE=%s",
  195. server_hash_encoded,
  196. server_nonce_encoded);
  197. tor_free(client_nonce);
  198. return 0;
  199. fail:
  200. connection_mark_for_close(TO_CONN(conn));
  201. return -1;
  202. }
  203. const control_cmd_syntax_t authenticate_syntax = {
  204. .max_args = 0,
  205. .accept_keywords=true,
  206. .kvline_flags=KV_OMIT_KEYS|KV_QUOTED_QSTRING,
  207. .store_raw_body=true
  208. };
  209. /** Called when we get an AUTHENTICATE message. Check whether the
  210. * authentication is valid, and if so, update the connection's state to
  211. * OPEN. Reply with DONE or ERROR.
  212. */
  213. int
  214. handle_control_authenticate(control_connection_t *conn,
  215. const control_cmd_args_t *args)
  216. {
  217. bool used_quoted_string = false;
  218. const or_options_t *options = get_options();
  219. const char *errstr = "Unknown error";
  220. char *password;
  221. size_t password_len;
  222. int bad_cookie=0, bad_password=0;
  223. smartlist_t *sl = NULL;
  224. if (args->kwargs == NULL) {
  225. password = tor_strdup("");
  226. password_len = 0;
  227. } else if (args->kwargs->next) {
  228. control_write_endreply(conn, 512, "Too many arguments to AUTHENTICATE.");
  229. connection_mark_for_close(TO_CONN(conn));
  230. return 0;
  231. } else if (strcmp(args->kwargs->key, "")) {
  232. control_write_endreply(conn, 512,
  233. "AUTHENTICATE does not accept keyword arguments.");
  234. connection_mark_for_close(TO_CONN(conn));
  235. return 0;
  236. } else if (strchr(args->raw_body, '\"')) {
  237. used_quoted_string = true;
  238. password = tor_strdup(args->kwargs->value);
  239. password_len = strlen(password);
  240. } else {
  241. const char *hex_passwd = args->kwargs->value;
  242. password_len = strlen(hex_passwd) / 2;
  243. password = tor_malloc(password_len+1);
  244. if (base16_decode(password, password_len+1, hex_passwd, strlen(hex_passwd))
  245. != (int) password_len) {
  246. control_write_endreply(conn, 551,
  247. "Invalid hexadecimal encoding. Maybe you tried a plain text "
  248. "password? If so, the standard requires that you put it in "
  249. "double quotes.");
  250. connection_mark_for_close(TO_CONN(conn));
  251. tor_free(password);
  252. return 0;
  253. }
  254. }
  255. if (conn->safecookie_client_hash != NULL) {
  256. /* The controller has chosen safe cookie authentication; the only
  257. * acceptable authentication value is the controller-to-server
  258. * response. */
  259. tor_assert(authentication_cookie_is_set);
  260. if (password_len != DIGEST256_LEN) {
  261. log_warn(LD_CONTROL,
  262. "Got safe cookie authentication response with wrong length "
  263. "(%d)", (int)password_len);
  264. errstr = "Wrong length for safe cookie response.";
  265. goto err;
  266. }
  267. if (tor_memneq(conn->safecookie_client_hash, password, DIGEST256_LEN)) {
  268. log_warn(LD_CONTROL,
  269. "Got incorrect safe cookie authentication response");
  270. errstr = "Safe cookie response did not match expected value.";
  271. goto err;
  272. }
  273. tor_free(conn->safecookie_client_hash);
  274. goto ok;
  275. }
  276. if (!options->CookieAuthentication && !options->HashedControlPassword &&
  277. !options->HashedControlSessionPassword) {
  278. /* if Tor doesn't demand any stronger authentication, then
  279. * the controller can get in with anything. */
  280. goto ok;
  281. }
  282. if (options->CookieAuthentication) {
  283. int also_password = options->HashedControlPassword != NULL ||
  284. options->HashedControlSessionPassword != NULL;
  285. if (password_len != AUTHENTICATION_COOKIE_LEN) {
  286. if (!also_password) {
  287. log_warn(LD_CONTROL, "Got authentication cookie with wrong length "
  288. "(%d)", (int)password_len);
  289. errstr = "Wrong length on authentication cookie.";
  290. goto err;
  291. }
  292. bad_cookie = 1;
  293. } else if (tor_memneq(authentication_cookie, password, password_len)) {
  294. if (!also_password) {
  295. log_warn(LD_CONTROL, "Got mismatched authentication cookie");
  296. errstr = "Authentication cookie did not match expected value.";
  297. goto err;
  298. }
  299. bad_cookie = 1;
  300. } else {
  301. goto ok;
  302. }
  303. }
  304. if (options->HashedControlPassword ||
  305. options->HashedControlSessionPassword) {
  306. int bad = 0;
  307. smartlist_t *sl_tmp;
  308. char received[DIGEST_LEN];
  309. int also_cookie = options->CookieAuthentication;
  310. sl = smartlist_new();
  311. if (options->HashedControlPassword) {
  312. sl_tmp = decode_hashed_passwords(options->HashedControlPassword);
  313. if (!sl_tmp)
  314. bad = 1;
  315. else {
  316. smartlist_add_all(sl, sl_tmp);
  317. smartlist_free(sl_tmp);
  318. }
  319. }
  320. if (options->HashedControlSessionPassword) {
  321. sl_tmp = decode_hashed_passwords(options->HashedControlSessionPassword);
  322. if (!sl_tmp)
  323. bad = 1;
  324. else {
  325. smartlist_add_all(sl, sl_tmp);
  326. smartlist_free(sl_tmp);
  327. }
  328. }
  329. if (bad) {
  330. if (!also_cookie) {
  331. log_warn(LD_BUG,
  332. "Couldn't decode HashedControlPassword: invalid base16");
  333. errstr="Couldn't decode HashedControlPassword value in configuration.";
  334. goto err;
  335. }
  336. bad_password = 1;
  337. SMARTLIST_FOREACH(sl, char *, str, tor_free(str));
  338. smartlist_free(sl);
  339. sl = NULL;
  340. } else {
  341. SMARTLIST_FOREACH(sl, char *, expected,
  342. {
  343. secret_to_key_rfc2440(received,DIGEST_LEN,
  344. password,password_len,expected);
  345. if (tor_memeq(expected + S2K_RFC2440_SPECIFIER_LEN,
  346. received, DIGEST_LEN))
  347. goto ok;
  348. });
  349. SMARTLIST_FOREACH(sl, char *, str, tor_free(str));
  350. smartlist_free(sl);
  351. sl = NULL;
  352. if (used_quoted_string)
  353. errstr = "Password did not match HashedControlPassword value from "
  354. "configuration";
  355. else
  356. errstr = "Password did not match HashedControlPassword value from "
  357. "configuration. Maybe you tried a plain text password? "
  358. "If so, the standard requires that you put it in double quotes.";
  359. bad_password = 1;
  360. if (!also_cookie)
  361. goto err;
  362. }
  363. }
  364. /** We only get here if both kinds of authentication failed. */
  365. tor_assert(bad_password && bad_cookie);
  366. log_warn(LD_CONTROL, "Bad password or authentication cookie on controller.");
  367. errstr = "Password did not match HashedControlPassword *or* authentication "
  368. "cookie.";
  369. err:
  370. tor_free(password);
  371. control_printf_endreply(conn, 515, "Authentication failed: %s", errstr);
  372. connection_mark_for_close(TO_CONN(conn));
  373. if (sl) { /* clean up */
  374. SMARTLIST_FOREACH(sl, char *, str, tor_free(str));
  375. smartlist_free(sl);
  376. }
  377. return 0;
  378. ok:
  379. log_info(LD_CONTROL, "Authenticated control connection ("TOR_SOCKET_T_FORMAT
  380. ")", conn->base_.s);
  381. send_control_done(conn);
  382. conn->base_.state = CONTROL_CONN_STATE_OPEN;
  383. tor_free(password);
  384. if (sl) { /* clean up */
  385. SMARTLIST_FOREACH(sl, char *, str, tor_free(str));
  386. smartlist_free(sl);
  387. }
  388. return 0;
  389. }
  390. void
  391. control_auth_free_all(void)
  392. {
  393. if (authentication_cookie) /* Free the auth cookie */
  394. tor_free(authentication_cookie);
  395. authentication_cookie_is_set = 0;
  396. }