comparison src/ciphers/anubis.c @ 381:999a5eb4ed10 libtomcrypt-dropbear

propagate from branch 'au.asn.ucc.matt.ltc.orig' (head 52840647ac7f5c707c3bd158d119a15734a7ef28) to branch 'au.asn.ucc.matt.ltc.dropbear' (head 20dccfc09627970a312d77fb41dc2970b62689c3)
author Matt Johnston <matt@ucc.asn.au>
date Thu, 11 Jan 2007 02:39:21 +0000
parents d5faf4814ddb
children
comparison
equal deleted inserted replaced
281:997e6f7dc01e 381:999a5eb4ed10
4 * algorithms in a highly modular and flexible manner. 4 * algorithms in a highly modular and flexible manner.
5 * 5 *
6 * The library is free for all purposes without any express 6 * The library is free for all purposes without any express
7 * guarantee it works. 7 * guarantee it works.
8 * 8 *
9 * Tom St Denis, [email protected], http://libtomcrypt.org 9 * Tom St Denis, [email protected], http://libtomcrypt.com
10 */ 10 */
11 11
12 /** 12 /**
13 @file anubis.c 13 @file anubis.c
14 Anubis implementation derived from public domain source 14 Anubis implementation derived from public domain source
27 &anubis_ecb_encrypt, 27 &anubis_ecb_encrypt,
28 &anubis_ecb_decrypt, 28 &anubis_ecb_decrypt,
29 &anubis_test, 29 &anubis_test,
30 &anubis_done, 30 &anubis_done,
31 &anubis_keysize, 31 &anubis_keysize,
32 NULL, NULL, NULL, NULL, NULL, NULL, NULL 32 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
33 }; 33 };
34 34
35 #define MIN_N 4 35 #define MIN_N 4
36 #define MAX_N 10 36 #define MAX_N 10
37 #define MIN_ROUNDS (8 + MIN_N) 37 #define MIN_ROUNDS (8 + MIN_N)
889 @param keylen The key length in bytes 889 @param keylen The key length in bytes
890 @param num_rounds The number of rounds desired (0 for default) 890 @param num_rounds The number of rounds desired (0 for default)
891 @param skey The key in as scheduled by this function. 891 @param skey The key in as scheduled by this function.
892 @return CRYPT_OK if successful 892 @return CRYPT_OK if successful
893 */ 893 */
894 #ifdef CLEAN_STACK 894 #ifdef LTC_CLEAN_STACK
895 static int _anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey) 895 static int _anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey)
896 #else 896 #else
897 int anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey) 897 int anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey)
898 #endif 898 #endif
899 { 899 {
942 */ 942 */
943 for (r = 0; r <= R; r++) { 943 for (r = 0; r <= R; r++) {
944 /* 944 /*
945 * generate r-th round key K^r: 945 * generate r-th round key K^r:
946 */ 946 */
947 K0 = T4[(kappa[N - 1] >> 24) ]; 947 K0 = T4[(kappa[N - 1] >> 24) & 0xff];
948 K1 = T4[(kappa[N - 1] >> 16) & 0xff]; 948 K1 = T4[(kappa[N - 1] >> 16) & 0xff];
949 K2 = T4[(kappa[N - 1] >> 8) & 0xff]; 949 K2 = T4[(kappa[N - 1] >> 8) & 0xff];
950 K3 = T4[(kappa[N - 1] ) & 0xff]; 950 K3 = T4[(kappa[N - 1] ) & 0xff];
951 for (i = N - 2; i >= 0; i--) { 951 for (i = N - 2; i >= 0; i--) {
952 K0 = T4[(kappa[i] >> 24) ] ^ 952 K0 = T4[(kappa[i] >> 24) & 0xff] ^
953 (T5[(K0 >> 24) ] & 0xff000000U) ^ 953 (T5[(K0 >> 24) & 0xff] & 0xff000000U) ^
954 (T5[(K0 >> 16) & 0xff] & 0x00ff0000U) ^ 954 (T5[(K0 >> 16) & 0xff] & 0x00ff0000U) ^
955 (T5[(K0 >> 8) & 0xff] & 0x0000ff00U) ^ 955 (T5[(K0 >> 8) & 0xff] & 0x0000ff00U) ^
956 (T5[(K0 ) & 0xff] & 0x000000ffU); 956 (T5[(K0 ) & 0xff] & 0x000000ffU);
957 K1 = T4[(kappa[i] >> 16) & 0xff] ^ 957 K1 = T4[(kappa[i] >> 16) & 0xff] ^
958 (T5[(K1 >> 24) ] & 0xff000000U) ^ 958 (T5[(K1 >> 24) & 0xff] & 0xff000000U) ^
959 (T5[(K1 >> 16) & 0xff] & 0x00ff0000U) ^ 959 (T5[(K1 >> 16) & 0xff] & 0x00ff0000U) ^
960 (T5[(K1 >> 8) & 0xff] & 0x0000ff00U) ^ 960 (T5[(K1 >> 8) & 0xff] & 0x0000ff00U) ^
961 (T5[(K1 ) & 0xff] & 0x000000ffU); 961 (T5[(K1 ) & 0xff] & 0x000000ffU);
962 K2 = T4[(kappa[i] >> 8) & 0xff] ^ 962 K2 = T4[(kappa[i] >> 8) & 0xff] ^
963 (T5[(K2 >> 24) ] & 0xff000000U) ^ 963 (T5[(K2 >> 24) & 0xff] & 0xff000000U) ^
964 (T5[(K2 >> 16) & 0xff] & 0x00ff0000U) ^ 964 (T5[(K2 >> 16) & 0xff] & 0x00ff0000U) ^
965 (T5[(K2 >> 8) & 0xff] & 0x0000ff00U) ^ 965 (T5[(K2 >> 8) & 0xff] & 0x0000ff00U) ^
966 (T5[(K2 ) & 0xff] & 0x000000ffU); 966 (T5[(K2 ) & 0xff] & 0x000000ffU);
967 K3 = T4[(kappa[i] ) & 0xff] ^ 967 K3 = T4[(kappa[i] ) & 0xff] ^
968 (T5[(K3 >> 24) ] & 0xff000000U) ^ 968 (T5[(K3 >> 24) & 0xff] & 0xff000000U) ^
969 (T5[(K3 >> 16) & 0xff] & 0x00ff0000U) ^ 969 (T5[(K3 >> 16) & 0xff] & 0x00ff0000U) ^
970 (T5[(K3 >> 8) & 0xff] & 0x0000ff00U) ^ 970 (T5[(K3 >> 8) & 0xff] & 0x0000ff00U) ^
971 (T5[(K3 ) & 0xff] & 0x000000ffU); 971 (T5[(K3 ) & 0xff] & 0x000000ffU);
972 } 972 }
973 /* 973 /*
974 -- this is the code to use with the large U tables: 974 -- this is the code to use with the large U tables:
975 K0 = K1 = K2 = K3 = 0; 975 K0 = K1 = K2 = K3 = 0;
976 for (i = 0; i < N; i++) { 976 for (i = 0; i < N; i++) {
977 K0 ^= U[i][(kappa[i] >> 24) ]; 977 K0 ^= U[i][(kappa[i] >> 24) & 0xff];
978 K1 ^= U[i][(kappa[i] >> 16) & 0xff]; 978 K1 ^= U[i][(kappa[i] >> 16) & 0xff];
979 K2 ^= U[i][(kappa[i] >> 8) & 0xff]; 979 K2 ^= U[i][(kappa[i] >> 8) & 0xff];
980 K3 ^= U[i][(kappa[i] ) & 0xff]; 980 K3 ^= U[i][(kappa[i] ) & 0xff];
981 } 981 }
982 */ 982 */
991 if (r == R) { 991 if (r == R) {
992 break; 992 break;
993 } 993 }
994 for (i = 0; i < N; i++) { 994 for (i = 0; i < N; i++) {
995 int j = i; 995 int j = i;
996 inter[i] = T0[(kappa[j--] >> 24) ]; if (j < 0) j = N - 1; 996 inter[i] = T0[(kappa[j--] >> 24) & 0xff]; if (j < 0) j = N - 1;
997 inter[i] ^= T1[(kappa[j--] >> 16) & 0xff]; if (j < 0) j = N - 1; 997 inter[i] ^= T1[(kappa[j--] >> 16) & 0xff]; if (j < 0) j = N - 1;
998 inter[i] ^= T2[(kappa[j--] >> 8) & 0xff]; if (j < 0) j = N - 1; 998 inter[i] ^= T2[(kappa[j--] >> 8) & 0xff]; if (j < 0) j = N - 1;
999 inter[i] ^= T3[(kappa[j ] ) & 0xff]; 999 inter[i] ^= T3[(kappa[j ] ) & 0xff];
1000 } 1000 }
1001 kappa[0] = inter[0] ^ rc[r]; 1001 kappa[0] = inter[0] ^ rc[r];
1013 } 1013 }
1014 for (r = 1; r < R; r++) { 1014 for (r = 1; r < R; r++) {
1015 for (i = 0; i < 4; i++) { 1015 for (i = 0; i < 4; i++) {
1016 v = skey->anubis.roundKeyEnc[R - r][i]; 1016 v = skey->anubis.roundKeyEnc[R - r][i];
1017 skey->anubis.roundKeyDec[r][i] = 1017 skey->anubis.roundKeyDec[r][i] =
1018 T0[T4[(v >> 24) ] & 0xff] ^ 1018 T0[T4[(v >> 24) & 0xff] & 0xff] ^
1019 T1[T4[(v >> 16) & 0xff] & 0xff] ^ 1019 T1[T4[(v >> 16) & 0xff] & 0xff] ^
1020 T2[T4[(v >> 8) & 0xff] & 0xff] ^ 1020 T2[T4[(v >> 8) & 0xff] & 0xff] ^
1021 T3[T4[(v ) & 0xff] & 0xff]; 1021 T3[T4[(v ) & 0xff] & 0xff];
1022 } 1022 }
1023 } 1023 }
1024 1024
1025 return CRYPT_OK; 1025 return CRYPT_OK;
1026 } 1026 }
1027 1027
1028 #ifdef CLEAN_STACK 1028 #ifdef LTC_CLEAN_STACK
1029 int anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey) 1029 int anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey)
1030 { 1030 {
1031 int err; 1031 int err;
1032 err = _anubis_setup(key, keylen, num_rounds, skey); 1032 err = _anubis_setup(key, keylen, num_rounds, skey);
1033 burn_stack(sizeof(int) * 5 + sizeof(ulong32) * (MAX_N + MAX_N + 5)); 1033 burn_stack(sizeof(int) * 5 + sizeof(ulong32) * (MAX_N + MAX_N + 5));
1058 /* 1058 /*
1059 * R - 1 full rounds: 1059 * R - 1 full rounds:
1060 */ 1060 */
1061 for (r = 1; r < R; r++) { 1061 for (r = 1; r < R; r++) {
1062 inter[0] = 1062 inter[0] =
1063 T0[(state[0] >> 24) ] ^ 1063 T0[(state[0] >> 24) & 0xff] ^
1064 T1[(state[1] >> 24) ] ^ 1064 T1[(state[1] >> 24) & 0xff] ^
1065 T2[(state[2] >> 24) ] ^ 1065 T2[(state[2] >> 24) & 0xff] ^
1066 T3[(state[3] >> 24) ] ^ 1066 T3[(state[3] >> 24) & 0xff] ^
1067 roundKey[r][0]; 1067 roundKey[r][0];
1068 inter[1] = 1068 inter[1] =
1069 T0[(state[0] >> 16) & 0xff] ^ 1069 T0[(state[0] >> 16) & 0xff] ^
1070 T1[(state[1] >> 16) & 0xff] ^ 1070 T1[(state[1] >> 16) & 0xff] ^
1071 T2[(state[2] >> 16) & 0xff] ^ 1071 T2[(state[2] >> 16) & 0xff] ^
1091 1091
1092 /* 1092 /*
1093 * last round: 1093 * last round:
1094 */ 1094 */
1095 inter[0] = 1095 inter[0] =
1096 (T0[(state[0] >> 24) ] & 0xff000000U) ^ 1096 (T0[(state[0] >> 24) & 0xff] & 0xff000000U) ^
1097 (T1[(state[1] >> 24) ] & 0x00ff0000U) ^ 1097 (T1[(state[1] >> 24) & 0xff] & 0x00ff0000U) ^
1098 (T2[(state[2] >> 24) ] & 0x0000ff00U) ^ 1098 (T2[(state[2] >> 24) & 0xff] & 0x0000ff00U) ^
1099 (T3[(state[3] >> 24) ] & 0x000000ffU) ^ 1099 (T3[(state[3] >> 24) & 0xff] & 0x000000ffU) ^
1100 roundKey[R][0]; 1100 roundKey[R][0];
1101 inter[1] = 1101 inter[1] =
1102 (T0[(state[0] >> 16) & 0xff] & 0xff000000U) ^ 1102 (T0[(state[0] >> 16) & 0xff] & 0xff000000U) ^
1103 (T1[(state[1] >> 16) & 0xff] & 0x00ff0000U) ^ 1103 (T1[(state[1] >> 16) & 0xff] & 0x00ff0000U) ^
1104 (T2[(state[2] >> 16) & 0xff] & 0x0000ff00U) ^ 1104 (T2[(state[2] >> 16) & 0xff] & 0x0000ff00U) ^
1132 /** 1132 /**
1133 Encrypts a block of text with Anubis 1133 Encrypts a block of text with Anubis
1134 @param pt The input plaintext (16 bytes) 1134 @param pt The input plaintext (16 bytes)
1135 @param ct The output ciphertext (16 bytes) 1135 @param ct The output ciphertext (16 bytes)
1136 @param skey The key as scheduled 1136 @param skey The key as scheduled
1137 @return CRYPT_OK if successful
1137 */ 1138 */
1138 void anubis_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey) 1139 int anubis_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey)
1139 { 1140 {
1140 LTC_ARGCHK(pt != NULL); 1141 LTC_ARGCHK(pt != NULL);
1141 LTC_ARGCHK(ct != NULL); 1142 LTC_ARGCHK(ct != NULL);
1142 LTC_ARGCHK(skey != NULL); 1143 LTC_ARGCHK(skey != NULL);
1143 anubis_crypt(pt, ct, skey->anubis.roundKeyEnc, skey->anubis.R); 1144 anubis_crypt(pt, ct, skey->anubis.roundKeyEnc, skey->anubis.R);
1145 return CRYPT_OK;
1144 } 1146 }
1145 1147
1146 /** 1148 /**
1147 Decrypts a block of text with Anubis 1149 Decrypts a block of text with Anubis
1148 @param ct The input ciphertext (16 bytes) 1150 @param ct The input ciphertext (16 bytes)
1149 @param pt The output plaintext (16 bytes) 1151 @param pt The output plaintext (16 bytes)
1150 @param skey The key as scheduled 1152 @param skey The key as scheduled
1153 @return CRYPT_OK if successful
1151 */ 1154 */
1152 void anubis_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey) 1155 int anubis_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey)
1153 { 1156 {
1154 LTC_ARGCHK(pt != NULL); 1157 LTC_ARGCHK(pt != NULL);
1155 LTC_ARGCHK(ct != NULL); 1158 LTC_ARGCHK(ct != NULL);
1156 LTC_ARGCHK(skey != NULL); 1159 LTC_ARGCHK(skey != NULL);
1157 anubis_crypt(ct, pt, skey->anubis.roundKeyDec, skey->anubis.R); 1160 anubis_crypt(ct, pt, skey->anubis.roundKeyDec, skey->anubis.R);
1161 return CRYPT_OK;
1158 } 1162 }
1159 1163
1160 /** 1164 /**
1161 Performs a self-test of the Anubis block cipher 1165 Performs a self-test of the Anubis block cipher
1162 @return CRYPT_OK if functional, CRYPT_NOP if self-test has been disabled 1166 @return CRYPT_OK if functional, CRYPT_NOP if self-test has been disabled
1494 1498
1495 for (x = 0; x < (int)(sizeof(tests)/sizeof(tests[0])); x++) { 1499 for (x = 0; x < (int)(sizeof(tests)/sizeof(tests[0])); x++) {
1496 anubis_setup(tests[x].key, tests[x].keylen, 0, &skey); 1500 anubis_setup(tests[x].key, tests[x].keylen, 0, &skey);
1497 anubis_ecb_encrypt(tests[x].pt, buf[0], &skey); 1501 anubis_ecb_encrypt(tests[x].pt, buf[0], &skey);
1498 anubis_ecb_decrypt(buf[0], buf[1], &skey); 1502 anubis_ecb_decrypt(buf[0], buf[1], &skey);
1499 if (memcmp(buf[0], tests[x].ct, 16) || memcmp(buf[1], tests[x].pt, 16)) { 1503 if (XMEMCMP(buf[0], tests[x].ct, 16) || XMEMCMP(buf[1], tests[x].pt, 16)) {
1500 return CRYPT_FAIL_TESTVECTOR; 1504 return CRYPT_FAIL_TESTVECTOR;
1501 } 1505 }
1502 1506
1503 for (y = 0; y < 1000; y++) anubis_ecb_encrypt(buf[0], buf[0], &skey); 1507 for (y = 0; y < 1000; y++) anubis_ecb_encrypt(buf[0], buf[0], &skey);
1504 for (y = 0; y < 1000; y++) anubis_ecb_decrypt(buf[0], buf[0], &skey); 1508 for (y = 0; y < 1000; y++) anubis_ecb_decrypt(buf[0], buf[0], &skey);
1505 if (memcmp(buf[0], tests[x].ct, 16)) { 1509 if (XMEMCMP(buf[0], tests[x].ct, 16)) {
1506 return CRYPT_FAIL_TESTVECTOR; 1510 return CRYPT_FAIL_TESTVECTOR;
1507 } 1511 }
1508 1512
1509 } 1513 }
1510 return CRYPT_OK; 1514 return CRYPT_OK;
1548 1552
1549 #endif 1553 #endif
1550 1554
1551 1555
1552 /* $Source: /cvs/libtom/libtomcrypt/src/ciphers/anubis.c,v $ */ 1556 /* $Source: /cvs/libtom/libtomcrypt/src/ciphers/anubis.c,v $ */
1553 /* $Revision: 1.7 $ */ 1557 /* $Revision: 1.15 $ */
1554 /* $Date: 2005/05/05 14:35:58 $ */ 1558 /* $Date: 2006/11/15 12:41:28 $ */