test_keygen.sh 9.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332
  1. #!/bin/sh
  2. # Note: some of this code is lifted from zero_length_keys.sh, and could be
  3. # unified.
  4. umask 077
  5. set -e
  6. if [ $# -eq 0 ] || [ ! -f ${1} ] || [ ! -x ${1} ]; then
  7. echo "Usage: ${0} PATH_TO_TOR [case-number]"
  8. exit 1
  9. elif [ $# -ge 1 ]; then
  10. TOR_BINARY="${1}"
  11. shift
  12. if [ $# -ge 1 ]; then
  13. dflt=0
  14. else
  15. dflt=1
  16. fi
  17. CASE2A=$dflt
  18. CASE2B=$dflt
  19. CASE3A=$dflt
  20. CASE3B=$dflt
  21. CASE3C=$dflt
  22. CASE4=$dflt
  23. CASE5=$dflt
  24. CASE6=$dflt
  25. CASE7=$dflt
  26. CASE8=$dflt
  27. CASE9=$dflt
  28. CASE10=$dflt
  29. if [ $# -ge 1 ]; then
  30. eval "CASE${1}"=1
  31. fi
  32. fi
  33. die() { echo "$1" >&2 ; exit 5; }
  34. check_dir() { [ -d "$1" ] || die "$1 did not exist"; }
  35. check_file() { [ -e "$1" ] || die "$1 did not exist"; }
  36. check_no_file() { [ -e "$1" ] && die "$1 was not supposed to exist" || true; }
  37. check_files_eq() { cmp "$1" "$2" || die "$1 and $2 did not match"; }
  38. check_keys_eq() { check_files_eq "${SRC}/keys/${1}" "${ME}/keys/${1}"; }
  39. DATA_DIR=`mktemp -d -t tor_keygen_tests.XXXXXX`
  40. if [ -z "$DATA_DIR" ]; then
  41. echo "Failure: mktemp invocation returned empty string" >&2
  42. exit 3
  43. fi
  44. if [ ! -d "$DATA_DIR" ]; then
  45. echo "Failure: mktemp invocation result doesn't point to directory" >&2
  46. exit 3
  47. fi
  48. trap "rm -rf '$DATA_DIR'" 0
  49. touch "${DATA_DIR}/empty_torrc"
  50. TOR="${TOR_BINARY} --hush --DisableNetwork 1 --ShutdownWaitLength 0 --ORPort 12345 --ExitRelay 0 -f ${DATA_DIR}/empty_torrc"
  51. # Step 1: Start Tor with --list-fingerprint. Make sure everything is there.
  52. mkdir "${DATA_DIR}/orig"
  53. ${TOR} --DataDirectory "${DATA_DIR}/orig" --list-fingerprint > /dev/null
  54. check_dir "${DATA_DIR}/orig/keys"
  55. check_file "${DATA_DIR}/orig/keys/ed25519_master_id_public_key"
  56. check_file "${DATA_DIR}/orig/keys/ed25519_master_id_secret_key"
  57. check_file "${DATA_DIR}/orig/keys/ed25519_signing_cert"
  58. check_file "${DATA_DIR}/orig/keys/ed25519_signing_secret_key"
  59. # Step 2: Start Tor with --keygen. Make sure everything is there.
  60. mkdir "${DATA_DIR}/keygen"
  61. ${TOR} --DataDirectory "${DATA_DIR}/keygen" --keygen --no-passphrase
  62. check_dir "${DATA_DIR}/keygen/keys"
  63. check_file "${DATA_DIR}/keygen/keys/ed25519_master_id_public_key"
  64. check_file "${DATA_DIR}/keygen/keys/ed25519_master_id_secret_key"
  65. check_file "${DATA_DIR}/keygen/keys/ed25519_signing_cert"
  66. check_file "${DATA_DIR}/keygen/keys/ed25519_signing_secret_key"
  67. # Step 3: Start Tor with --keygen and a passphrase.
  68. # Make sure everything is there.
  69. mkdir "${DATA_DIR}/encrypted"
  70. echo "passphrase" | ${TOR} --DataDirectory "${DATA_DIR}/encrypted" --keygen --passphrase-fd 0
  71. check_dir "${DATA_DIR}/encrypted/keys"
  72. check_file "${DATA_DIR}/encrypted/keys/ed25519_master_id_public_key"
  73. check_file "${DATA_DIR}/encrypted/keys/ed25519_master_id_secret_key_encrypted"
  74. check_file "${DATA_DIR}/encrypted/keys/ed25519_signing_cert"
  75. check_file "${DATA_DIR}/encrypted/keys/ed25519_signing_secret_key"
  76. echo "KEY GENERATION WAS SUCCESSFUL."
  77. #
  78. # The "case X" numbers below come from s7r's email on
  79. # https://lists.torproject.org/pipermail/tor-dev/2015-August/009204.html
  80. # Case 2a: Missing secret key, public key exists, start tor.
  81. if [ "$CASE2A" = 1 ]; then
  82. ME="${DATA_DIR}/case2a"
  83. SRC="${DATA_DIR}/orig"
  84. mkdir -p "${ME}/keys"
  85. cp "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/"
  86. ${TOR} --DataDirectory "${ME}" --list-fingerprint && die "Somehow succeeded when missing secret key, certs" || true
  87. check_files_eq "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/ed25519_master_id_public_key"
  88. echo "==== Case 2A ok"
  89. fi
  90. # Case 2b: Encrypted secret key, public key exists, start tor.
  91. if [ "$CASE2B" = 1 ]; then
  92. ME="${DATA_DIR}/case2b"
  93. SRC="${DATA_DIR}/encrypted"
  94. mkdir -p "${ME}/keys"
  95. cp "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/"
  96. cp "${SRC}/keys/ed25519_master_id_secret_key_encrypted" "${ME}/keys/"
  97. ${TOR} --DataDirectory "${ME}" --list-fingerprint && dir "Somehow succeeded with encrypted secret key, missing certs"
  98. check_files_eq "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/ed25519_master_id_public_key"
  99. check_files_eq "${SRC}/keys/ed25519_master_id_secret_key_encrypted" "${ME}/keys/ed25519_master_id_secret_key_encrypted"
  100. echo "==== Case 2B ok"
  101. fi
  102. # Case 3a: Start Tor with only master key.
  103. if [ "$CASE3A" = 1 ]; then
  104. ME="${DATA_DIR}/case3a"
  105. SRC="${DATA_DIR}/orig"
  106. mkdir -p "${ME}/keys"
  107. cp "${SRC}/keys/ed25519_master_id_"* "${ME}/keys/"
  108. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Tor failed when starting with only master key"
  109. check_files_eq "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/ed25519_master_id_public_key"
  110. check_files_eq "${SRC}/keys/ed25519_master_id_secret_key" "${ME}/keys/ed25519_master_id_secret_key"
  111. check_file "${ME}/keys/ed25519_signing_cert"
  112. check_file "${ME}/keys/ed25519_signing_secret_key"
  113. echo "==== Case 3A ok"
  114. fi
  115. # Case 3b: Call keygen with only unencrypted master key.
  116. if [ "$CASE3B" = 1 ]; then
  117. ME="${DATA_DIR}/case3b"
  118. SRC="${DATA_DIR}/orig"
  119. mkdir -p "${ME}/keys"
  120. cp "${SRC}/keys/ed25519_master_id_"* "${ME}/keys/"
  121. ${TOR} --DataDirectory "${ME}" --keygen || die "Keygen failed with only master key"
  122. check_files_eq "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/ed25519_master_id_public_key"
  123. check_files_eq "${SRC}/keys/ed25519_master_id_secret_key" "${ME}/keys/ed25519_master_id_secret_key"
  124. check_file "${ME}/keys/ed25519_signing_cert"
  125. check_file "${ME}/keys/ed25519_signing_secret_key"
  126. echo "==== Case 3B ok"
  127. fi
  128. # Case 3c: Call keygen with only encrypted master key.
  129. if [ "$CASE3C" = 1 ]; then
  130. ME="${DATA_DIR}/case3c"
  131. SRC="${DATA_DIR}/encrypted"
  132. mkdir -p "${ME}/keys"
  133. cp "${SRC}/keys/ed25519_master_id_"* "${ME}/keys/"
  134. echo "passphrase" | ${TOR} --DataDirectory "${ME}" --keygen --passphrase-fd 0 || die "Keygen failed with only encrypted master key"
  135. check_files_eq "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/ed25519_master_id_public_key"
  136. check_files_eq "${SRC}/keys/ed25519_master_id_secret_key_encrypted" "${ME}/keys/ed25519_master_id_secret_key_encrypted"
  137. check_file "${ME}/keys/ed25519_signing_cert"
  138. check_file "${ME}/keys/ed25519_signing_secret_key"
  139. echo "==== Case 3C ok"
  140. fi
  141. # Case 4: Make a new data directory with only an unencrypted secret key.
  142. # Then start tor. The rest should become correct.
  143. if [ "$CASE4" = 1 ]; then
  144. ME="${DATA_DIR}/case4"
  145. SRC="${DATA_DIR}/orig"
  146. mkdir -p "${ME}/keys"
  147. cp "${SRC}/keys/ed25519_master_id_secret_key" "${ME}/keys/"
  148. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Tor wouldn't start with only unencrypted secret key"
  149. check_file "${ME}/keys/ed25519_master_id_public_key"
  150. check_file "${ME}/keys/ed25519_master_id_signing_cert"
  151. check_file "${ME}/keys/ed25519_master_id_signing_secret_key"
  152. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Tor wouldn't start again after starting once with only unencrypted secret key."
  153. echo "==== Case 4 ok"
  154. fi
  155. # Case 5: Make a new data directory with only an encrypted secret key.
  156. if [ "$CASE5" = 1 ]; then
  157. ME="${DATA_DIR}/case5"
  158. SRC="${DATA_DIR}/encrypted"
  159. mkdir -p "${ME}/keys"
  160. cp "${SRC}/keys/ed25519_master_id_secret_key_encrypted" "${ME}/keys/"
  161. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Tor wouldn't start with only encrypted secret key"
  162. check_files_eq "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/ed25519_master_id_public_key"
  163. echo "==== Case 5 ok"
  164. fi
  165. # Case 6: Make a new data directory with encrypted secret key and public key
  166. if [ "$CASE6" = 1 ]; then
  167. ME="${DATA_DIR}/case6"
  168. SRC="${DATA_DIR}/encrypted"
  169. mkdir -p "${ME}/keys"
  170. cp "${SRC}/keys/ed25519_master_id_secret_key_encrypted" "${ME}/keys/"
  171. cp "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/"
  172. ${TOR} --DataDirectory "${ME}" --list-fingerprint && die "Tor started with encrypted secret key and no certs" || true
  173. check_no_file "${ME}/keys/ed25519_signing_cert"
  174. check_no_file "${ME}/keys/ed25519_signing_secret_key"
  175. echo "==== Case 6 ok"
  176. fi
  177. # Case 7: Make a new data directory with unencrypted secret key and
  178. # certificates; missing master public.
  179. if [ "$CASE7" = 1 ]; then
  180. ME="${DATA_DIR}/case7"
  181. SRC="${DATA_DIR}/keygen"
  182. mkdir -p "${ME}/keys"
  183. cp "${SRC}/keys/ed25519_master_id_secret_key" "${ME}/keys/"
  184. cp "${SRC}/keys/ed25519_signing_cert" "${ME}/keys/"
  185. cp "${SRC}/keys/ed25519_signing_secret_key" "${ME}/keys/"
  186. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Failed when starting with missing public key"
  187. check_keys_eq ed25519_master_id_secret_key
  188. check_keys_eq ed25519_master_id_public_key
  189. check_keys_eq ed25519_signing_secret_key
  190. check_keys_eq ed25519_signing_cert
  191. echo "==== Case 7 ok"
  192. fi
  193. # Case 8: offline master secret key.
  194. if [ "$CASE8" = 1 ]; then
  195. ME="${DATA_DIR}/case8"
  196. SRC="${DATA_DIR}/keygen"
  197. mkdir -p "${ME}/keys"
  198. cp "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/"
  199. cp "${SRC}/keys/ed25519_signing_cert" "${ME}/keys/"
  200. cp "${SRC}/keys/ed25519_signing_secret_key" "${ME}/keys/"
  201. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Failed when starting with offline secret key"
  202. check_no_file "${ME}/keys/ed25519_master_id_secret_key"
  203. check_keys_eq ed25519_master_id_public_key
  204. check_keys_eq ed25519_signing_secret_key
  205. check_keys_eq ed25519_signing_cert
  206. echo "==== Case 8 ok"
  207. fi
  208. # Case 9: signing cert and secret key provided; could infer master key.
  209. if [ "$CASE9" = 1 ]; then
  210. ME="${DATA_DIR}/case9"
  211. SRC="${DATA_DIR}/keygen"
  212. mkdir -p "${ME}/keys"
  213. cp "${SRC}/keys/ed25519_signing_cert" "${ME}/keys/"
  214. cp "${SRC}/keys/ed25519_signing_secret_key" "${ME}/keys/"
  215. ${TOR} --DataDirectory "${ME}" --list-fingerprint || die "Failed when starting with only signing material"
  216. check_no_file "${ME}/keys/ed25519_master_id_secret_key"
  217. check_keys_eq ed25519_master_id_public_key
  218. check_keys_eq ed25519_signing_secret_key
  219. check_keys_eq ed25519_signing_cert
  220. echo "==== Case 9 ok"
  221. fi
  222. # Case 10: key mismatch.
  223. if [ "$CASE10" = 1 ]; then
  224. ME="${DATA_DIR}/case10"
  225. SRC="${DATA_DIR}/keygen"
  226. OTHER="${DATA_DIR}/orig"
  227. mkdir -p "${ME}/keys"
  228. cp "${SRC}/keys/ed25519_master_id_public_key" "${ME}/keys/"
  229. cp "${OTHER}/keys/ed25519_master_id_secret_key" "${ME}/keys/"
  230. ${TOR} --DataDirectory "${ME}" --list-fingerprint && die "Successfully started with mismatched keys!?" || true
  231. echo "==== Case 10 ok"
  232. fi
  233. # Check cert-only.