From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: From: Serge Petrenko Subject: [PATCH] Introduce a function to reencode scramble. Date: Tue, 30 Oct 2018 10:37:26 +0300 Message-Id: <20181030073726.26822-1-sergepetrenko@tarantool.org> To: vdavydov.dev@gmail.com, kostja@tarantool.org Cc: tarantool-patches@freelists.org, Serge Petrenko List-ID: Introduce a new function, scramble_reencode(), which allows one cluster instance to reencode a scramble received from a client using the salt from another cluster instance. This is needed for proxy to mimic client connections when connecting to remote instances. Part of #2625 --- https://github.com/tarantool/tarantool/tree/sp/scramble-reencode https://github.com/tarantool/tarantool/issues/2625 src/scramble.c | 23 +++++++++++++++++++++++ src/scramble.h | 9 +++++++++ test/unit/scramble.c | 10 ++++++++++ test/unit/scramble.result | 1 + 4 files changed, 43 insertions(+) diff --git a/src/scramble.c b/src/scramble.c index ca1f98793..6dc43932b 100644 --- a/src/scramble.c +++ b/src/scramble.c @@ -67,6 +67,29 @@ scramble_prepare(void *out, const void *salt, const void *password, xor(out, hash1, out, SCRAMBLE_SIZE); } +void +scramble_reencode(void *out, const void *in, const void *salt, const void *msalt, + const void *hash2) +{ + unsigned char hash1[SCRAMBLE_SIZE]; + unsigned char sh[SCRAMBLE_SIZE]; + SHA1_CTX ctx; + + SHA1Init(&ctx); + SHA1Update(&ctx, salt, SCRAMBLE_SIZE); + SHA1Update(&ctx, hash2, SCRAMBLE_SIZE); + SHA1Final(sh, &ctx); + + xor(hash1, in, sh, SCRAMBLE_SIZE); + + SHA1Init(&ctx); + SHA1Update(&ctx, msalt, SCRAMBLE_SIZE); + SHA1Update(&ctx, hash2, SCRAMBLE_SIZE); + SHA1Final(out, &ctx); + + xor(out, hash1, out, SCRAMBLE_SIZE); +} + int scramble_check(const void *scramble, const void *salt, const void *hash2) { diff --git a/src/scramble.h b/src/scramble.h index 7dee31483..e47870f8e 100644 --- a/src/scramble.h +++ b/src/scramble.h @@ -89,6 +89,15 @@ scramble_check(const void *scramble, const void *salt, const void *hash2); void password_prepare(const char *password, int len, char *out, int out_len); +/** + * Given a scramble received from a client, salt sent to client, + * salt received from another instance and user hash2, recalculate + * a scramble to be sent to a remote instance for authentication. + */ +void +scramble_reencode(void *out, const void *in, const void *salt, const void *msalt, + const void *hash2); + #if defined(__cplusplus) } /* extern "C" */ #endif diff --git a/test/unit/scramble.c b/test/unit/scramble.c index 572466e9b..8f1ee55af 100644 --- a/test/unit/scramble.c +++ b/test/unit/scramble.c @@ -32,6 +32,16 @@ test_scramble() printf("%d\n", scramble_check(scramble, salt, hash2)); + int remote_salt[SCRAMBLE_SIZE/sizeof(int)]; + for(size_t i = 0; i < sizeof(salt)/sizeof(int); ++i) + remote_salt[i] = rand(); + + char new_scramble[SCRAMBLE_SIZE]; + + scramble_reencode(new_scramble, scramble, salt, remote_salt, hash2); + + printf("%d\n", scramble_check(new_scramble, remote_salt, hash2)); + password = "wrongpass"; scramble_prepare(scramble, salt, password, strlen(password)); diff --git a/test/unit/scramble.result b/test/unit/scramble.result index 986394f7c..0463db267 100644 --- a/test/unit/scramble.result +++ b/test/unit/scramble.result @@ -1,3 +1,4 @@ 0 +0 1 1 -- 2.17.1 (Apple Git-112)