From 52962f3a5e5265a06e11478888d24230bd720a1d Mon Sep 17 00:00:00 2001 From: Cory McWilliams Date: Sat, 11 May 2024 09:50:00 -0400 Subject: [PATCH] Remove the :auth key. We can sign JWTs with :admin, and it's one less magic key. --- src/httpd.js.c | 34 +++++++++++++++------------------- src/ssb.db.c | 2 +- 2 files changed, 16 insertions(+), 20 deletions(-) diff --git a/src/httpd.js.c b/src/httpd.js.c index 961df4a8..38798e9b 100644 --- a/src/httpd.js.c +++ b/src/httpd.js.c @@ -1080,7 +1080,7 @@ static JSValue _authenticate_jwt(JSContext* context, const char* jwt) tf_task_t* task = tf_task_get(context); tf_ssb_t* ssb = tf_task_get_ssb(task); char public_key_b64[k_id_base64_len] = { 0 }; - tf_ssb_db_identity_visit(ssb, ":auth", _public_key_visit, public_key_b64); + tf_ssb_db_identity_visit(ssb, ":admin", _public_key_visit, public_key_b64); const char* payload = jwt + dot[0] + 1; size_t payload_length = dot[1] - dot[0] - 1; @@ -1150,15 +1150,12 @@ static void _visit_auth_identity(const char* identity, void* user_data) static bool _get_auth_private_key(tf_ssb_t* ssb, uint8_t* out_private_key) { char id[k_id_base64_len] = { 0 }; - tf_ssb_db_identity_visit(ssb, ":auth", _visit_auth_identity, id); + tf_ssb_db_identity_visit(ssb, ":admin", _visit_auth_identity, id); if (*id) { - return tf_ssb_db_identity_get_private_key(ssb, ":auth", id, out_private_key, crypto_sign_SECRETKEYBYTES); - } - else - { - return tf_ssb_db_identity_create(ssb, ":auth", out_private_key + crypto_sign_PUBLICKEYBYTES, out_private_key); + return tf_ssb_db_identity_get_private_key(ssb, ":admin", id, out_private_key, crypto_sign_SECRETKEYBYTES); } + return false; } static const char* _make_session_jwt(tf_ssb_t* ssb, const char* name) @@ -1167,21 +1164,15 @@ static const char* _make_session_jwt(tf_ssb_t* ssb, const char* name) { return NULL; } - uint8_t private_key[crypto_sign_SECRETKEYBYTES] = { 0 }; - if (!_get_auth_private_key(ssb, private_key)) - { - return NULL; - } uv_timespec64_t now = { 0 }; uv_clock_gettime(UV_CLOCK_REALTIME, &now); - JSContext* context = tf_ssb_get_context(ssb); - const char* header_json = "{\"alg\":\"HS256\",\"typ\":\"JWT\"}"; char header_base64[256]; sodium_bin2base64(header_base64, sizeof(header_base64), (uint8_t*)header_json, strlen(header_json), sodium_base64_VARIANT_URLSAFE_NO_PADDING); + JSContext* context = tf_ssb_get_context(ssb); JSValue payload = JS_NewObject(context); JS_SetPropertyStr(context, payload, "name", JS_NewString(context, name)); JS_SetPropertyStr(context, payload, "exp", JS_NewInt64(context, now.tv_sec * 1000 + now.tv_nsec / 1000000LL + k_refresh_interval)); @@ -1196,12 +1187,17 @@ static const char* _make_session_jwt(tf_ssb_t* ssb, const char* name) unsigned long long signature_length = 0; char signature_base64[256] = { 0 }; - if (crypto_sign_detached(signature, &signature_length, (const uint8_t*)payload_base64, strlen(payload_base64), private_key) == 0) + uint8_t private_key[crypto_sign_SECRETKEYBYTES] = { 0 }; + if (_get_auth_private_key(ssb, private_key)) { - sodium_bin2base64(signature_base64, sizeof(signature_base64), signature, sizeof(signature), sodium_base64_VARIANT_URLSAFE_NO_PADDING); - size_t size = strlen(header_base64) + 1 + strlen(payload_base64) + 1 + strlen(signature_base64) + 1; - result = tf_malloc(size); - snprintf(result, size, "%s.%s.%s", header_base64, payload_base64, signature_base64); + if (crypto_sign_detached(signature, &signature_length, (const uint8_t*)payload_base64, strlen(payload_base64), private_key) == 0) + { + sodium_bin2base64(signature_base64, sizeof(signature_base64), signature, sizeof(signature), sodium_base64_VARIANT_URLSAFE_NO_PADDING); + size_t size = strlen(header_base64) + 1 + strlen(payload_base64) + 1 + strlen(signature_base64) + 1; + result = tf_malloc(size); + snprintf(result, size, "%s.%s.%s", header_base64, payload_base64, signature_base64); + } + sodium_memzero(private_key, sizeof(private_key)); } JS_FreeCString(context, payload_string); diff --git a/src/ssb.db.c b/src/ssb.db.c index 4ab57dcf..eb40e0bb 100644 --- a/src/ssb.db.c +++ b/src/ssb.db.c @@ -163,6 +163,7 @@ void tf_ssb_db_init(tf_ssb_t* ssb) " private_key TEXT UNIQUE" ")"); _tf_ssb_db_exec(db, "CREATE INDEX IF NOT EXISTS identities_user ON identities (user, public_key)"); + _tf_ssb_db_exec(db, "DELETE FROM identities WHERE user = ':auth'"); bool populate_fts = false; if (!_tf_ssb_db_has_rows(db, "PRAGMA table_list('messages_fts')")) @@ -1623,7 +1624,6 @@ bool tf_ssb_db_set_account_password(tf_ssb_t* ssb, const char* name, const char* if (sqlite3_bind_text(statement, 1, name, -1, NULL) == SQLITE_OK && sqlite3_bind_text(statement, 2, user_string, user_length, NULL) == SQLITE_OK) { result = sqlite3_step(statement) == SQLITE_DONE; - tf_printf("set account password = %d\n", result); } sqlite3_finalize(statement); }