comparison libpurple/cipher.c @ 21907:03463c52b9d7

Triple DES cipher support from Elliott Sales de Andrade committer: Gary Kramlich <grim@reaperworld.com>
author Elliott Sales de Andrade <qulogic@pidgin.im>
date Thu, 20 Dec 2007 03:40:56 +0000
parents 787b3897ba9f
children f786e478e08b
comparison
equal deleted inserted replaced
21906:47aabef7f802 21907:03463c52b9d7
338 NULL, /* decrypt */ 338 NULL, /* decrypt */
339 NULL, /* set salt */ 339 NULL, /* set salt */
340 NULL, /* get salt size */ 340 NULL, /* get salt size */
341 NULL, /* set key */ 341 NULL, /* set key */
342 NULL, /* get key size */ 342 NULL, /* get key size */
343 NULL, /* set batch mode */
344 NULL, /* get batch mode */
343 345
344 /* padding */ 346 /* padding */
345 NULL,
346 NULL,
347 NULL, 347 NULL,
348 NULL 348 NULL
349 }; 349 };
350 350
351 /******************************************************************************* 351 /*******************************************************************************
593 NULL, /* decrypt */ 593 NULL, /* decrypt */
594 NULL, /* set salt */ 594 NULL, /* set salt */
595 NULL, /* get salt size */ 595 NULL, /* get salt size */
596 NULL, /* set key */ 596 NULL, /* set key */
597 NULL, /* get key size */ 597 NULL, /* get key size */
598 NULL, /* set batch mode */
599 NULL, /* get batch mode */
598 600
599 /* padding */ 601 /* padding */
600 NULL,
601 NULL,
602 NULL, 602 NULL,
603 NULL 603 NULL
604 }; 604 };
605 605
606 /****************************************************************************** 606 /******************************************************************************
984 0); 984 0);
985 } 985 }
986 return 0; 986 return 0;
987 } 987 }
988 988
989 static gint
990 des_decrypt(PurpleCipherContext *context, const guchar data[],
991 size_t len, guchar output[], size_t *outlen) {
992 int offset = 0;
993 int i = 0;
994 int tmp;
995 guint8 buf[8] = {0,0,0,0,0,0,0,0};
996 while(offset+8<=len) {
997 des_ecb_crypt(purple_cipher_context_get_data(context),
998 data+offset,
999 output+offset,
1000 1);
1001 offset+=8;
1002 }
1003 *outlen = len;
1004 if(offset<len) {
1005 *outlen += len - offset;
1006 tmp = offset;
1007 while(tmp<len) {
1008 buf[i++] = data[tmp];
1009 tmp++;
1010 }
1011 des_ecb_crypt(purple_cipher_context_get_data(context),
1012 buf,
1013 output+offset,
1014 1);
1015 }
1016 return 0;
1017 }
1018
989 static void 1019 static void
990 des_init(PurpleCipherContext *context, gpointer extra) { 1020 des_init(PurpleCipherContext *context, gpointer extra) {
991 struct _des_ctx *mctx; 1021 struct _des_ctx *mctx;
992 mctx = g_new0(struct _des_ctx, 1); 1022 mctx = g_new0(struct _des_ctx, 1);
993 purple_cipher_context_set_data(context, mctx); 1023 purple_cipher_context_set_data(context, mctx);
1003 g_free(des_context); 1033 g_free(des_context);
1004 des_context = NULL; 1034 des_context = NULL;
1005 } 1035 }
1006 1036
1007 static PurpleCipherOps DESOps = { 1037 static PurpleCipherOps DESOps = {
1008 NULL, /* Set option */ 1038 NULL, /* Set option */
1009 NULL, /* Get option */ 1039 NULL, /* Get option */
1010 des_init, /* init */ 1040 des_init, /* init */
1011 NULL, /* reset */ 1041 NULL, /* reset */
1012 des_uninit, /* uninit */ 1042 des_uninit, /* uninit */
1013 NULL, /* set iv */ 1043 NULL, /* set iv */
1014 NULL, /* append */ 1044 NULL, /* append */
1015 NULL, /* digest */ 1045 NULL, /* digest */
1016 des_encrypt, /* encrypt */ 1046 des_encrypt, /* encrypt */
1017 NULL, /* decrypt */ 1047 des_decrypt, /* decrypt */
1018 NULL, /* set salt */ 1048 NULL, /* set salt */
1019 NULL, /* get salt size */ 1049 NULL, /* get salt size */
1020 des_set_key, /* set key */ 1050 des_set_key, /* set key */
1021 NULL, /* get key size */ 1051 NULL, /* get key size */
1052 NULL, /* set batch mode */
1053 NULL, /* get batch mode */
1022 1054
1023 /* padding */ 1055 /* padding */
1024 NULL,
1025 NULL,
1026 NULL, 1056 NULL,
1027 NULL 1057 NULL
1028 }; 1058 };
1029 1059
1060 /******************************************************************************
1061 * Triple-DES
1062 *****************************************************************************/
1063
1064 typedef struct _des3_ctx
1065 {
1066 PurpleCipherBatchMode mode;
1067 guchar iv[8];
1068 /* First key for encryption */
1069 struct _des_ctx key1;
1070 /* Second key for decryption */
1071 struct _des_ctx key2;
1072 /* Third key for encryption */
1073 struct _des_ctx key3;
1074 } des3_ctx[1];
1075
1076 /*
1077 * Fill a DES3 context with subkeys calculated from 3 64bit key.
1078 * Does not check parity bits, but simply ignore them.
1079 * Does not check for weak keys.
1080 **/
1081 static void
1082 des3_set_key(PurpleCipherContext *context, const guchar * key)
1083 {
1084 struct _des3_ctx *ctx = purple_cipher_context_get_data(context);
1085 int i;
1086
1087 des_key_schedule (key + 0, ctx->key1.encrypt_subkeys);
1088 des_key_schedule (key + 8, ctx->key2.encrypt_subkeys);
1089 des_key_schedule (key + 16, ctx->key3.encrypt_subkeys);
1090
1091 for (i = 0; i < 32; i += 2)
1092 {
1093 ctx->key1.decrypt_subkeys[i] = ctx->key1.encrypt_subkeys[30-i];
1094 ctx->key1.decrypt_subkeys[i+1] = ctx->key1.encrypt_subkeys[31-i];
1095 ctx->key2.decrypt_subkeys[i] = ctx->key2.encrypt_subkeys[30-i];
1096 ctx->key2.decrypt_subkeys[i+1] = ctx->key2.encrypt_subkeys[31-i];
1097 ctx->key3.decrypt_subkeys[i] = ctx->key3.encrypt_subkeys[30-i];
1098 ctx->key3.decrypt_subkeys[i+1] = ctx->key3.encrypt_subkeys[31-i];
1099 }
1100 }
1101
1102 static gint
1103 des3_ecb_encrypt(struct _des3_ctx *ctx, const guchar data[],
1104 size_t len, guchar output[], size_t *outlen)
1105 {
1106 int offset = 0;
1107 int i = 0;
1108 int tmp;
1109 guint8 buf[8] = {0,0,0,0,0,0,0,0};
1110 while (offset + 8 <= len) {
1111 des_ecb_crypt(&ctx->key1,
1112 data+offset,
1113 output+offset,
1114 0);
1115 des_ecb_crypt(&ctx->key2,
1116 output+offset,
1117 buf,
1118 1);
1119 des_ecb_crypt(&ctx->key3,
1120 buf,
1121 output+offset,
1122 0);
1123 offset += 8;
1124 }
1125 *outlen = len;
1126 if (offset < len) {
1127 *outlen += len - offset;
1128 tmp = offset;
1129 memset(buf, 0, 8);
1130 while (tmp < len) {
1131 buf[i++] = data[tmp];
1132 tmp++;
1133 }
1134 des_ecb_crypt(&ctx->key1,
1135 buf,
1136 output+offset,
1137 0);
1138 des_ecb_crypt(&ctx->key2,
1139 output+offset,
1140 buf,
1141 1);
1142 des_ecb_crypt(&ctx->key3,
1143 buf,
1144 output+offset,
1145 0);
1146 }
1147 return 0;
1148 }
1149
1150 static gint
1151 des3_cbc_encrypt(struct _des3_ctx *ctx, const guchar data[],
1152 size_t len, guchar output[], size_t *outlen)
1153 {
1154 int offset = 0;
1155 int i = 0;
1156 int tmp;
1157 guint8 buf[8];
1158 memcpy(buf, ctx->iv, 8);
1159 while (offset + 8 <= len) {
1160 for (i = 0; i < 8; i++)
1161 buf[i] ^= data[offset + i];
1162 des_ecb_crypt(&ctx->key1,
1163 buf,
1164 output+offset,
1165 0);
1166 des_ecb_crypt(&ctx->key2,
1167 output+offset,
1168 buf,
1169 1);
1170 des_ecb_crypt(&ctx->key3,
1171 buf,
1172 output+offset,
1173 0);
1174 memcpy(buf, output+offset, 8);
1175 offset += 8;
1176 }
1177 *outlen = len;
1178 if (offset < len) {
1179 *outlen += len - offset;
1180 tmp = offset;
1181 i = 0;
1182 while (tmp < len) {
1183 buf[i++] ^= data[tmp];
1184 tmp++;
1185 }
1186 des_ecb_crypt(&ctx->key1,
1187 buf,
1188 output+offset,
1189 0);
1190 des_ecb_crypt(&ctx->key2,
1191 output+offset,
1192 buf,
1193 1);
1194 des_ecb_crypt(&ctx->key3,
1195 buf,
1196 output+offset,
1197 0);
1198 }
1199 return 0;
1200 }
1201
1202 static gint
1203 des3_encrypt(PurpleCipherContext *context, const guchar data[],
1204 size_t len, guchar output[], size_t *outlen)
1205 {
1206 struct _des3_ctx *ctx = purple_cipher_context_get_data(context);
1207
1208 if (ctx->mode == PURPLE_CIPHER_BATCH_MODE_ECB) {
1209 return des3_ecb_encrypt(ctx, data, len, output, outlen);
1210 } else if (ctx->mode == PURPLE_CIPHER_BATCH_MODE_CBC) {
1211 return des3_cbc_encrypt(ctx, data, len, output, outlen);
1212 } else {
1213 g_return_val_if_reached(0);
1214 }
1215
1216 return 0;
1217 }
1218
1219 static gint
1220 des3_ecb_decrypt(struct _des3_ctx *ctx, const guchar data[],
1221 size_t len, guchar output[], size_t *outlen)
1222 {
1223 int offset = 0;
1224 int i = 0;
1225 int tmp;
1226 guint8 buf[8] = {0,0,0,0,0,0,0,0};
1227 while (offset + 8 <= len) {
1228 /* NOTE: Apply key in reverse */
1229 des_ecb_crypt(&ctx->key3,
1230 data+offset,
1231 output+offset,
1232 1);
1233 des_ecb_crypt(&ctx->key2,
1234 output+offset,
1235 buf,
1236 0);
1237 des_ecb_crypt(&ctx->key1,
1238 buf,
1239 output+offset,
1240 1);
1241 offset+=8;
1242 }
1243 *outlen = len;
1244 if (offset < len) {
1245 *outlen += len - offset;
1246 tmp = offset;
1247 memset(buf, 0, 8);
1248 while (tmp < len) {
1249 buf[i++] = data[tmp];
1250 tmp++;
1251 }
1252 des_ecb_crypt(&ctx->key3,
1253 buf,
1254 output+offset,
1255 1);
1256 des_ecb_crypt(&ctx->key2,
1257 output+offset,
1258 buf,
1259 0);
1260 des_ecb_crypt(&ctx->key1,
1261 buf,
1262 output+offset,
1263 1);
1264 }
1265 return 0;
1266 }
1267
1268 static gint
1269 des3_cbc_decrypt(struct _des3_ctx *ctx, const guchar data[],
1270 size_t len, guchar output[], size_t *outlen)
1271 {
1272 int offset = 0;
1273 int i = 0;
1274 int tmp;
1275 guint8 buf[8] = {0,0,0,0,0,0,0,0};
1276 guint8 link[8];
1277 memcpy(link, ctx->iv, 8);
1278 while (offset + 8 <= len) {
1279 des_ecb_crypt(&ctx->key3,
1280 data+offset,
1281 output+offset,
1282 1);
1283 des_ecb_crypt(&ctx->key2,
1284 output+offset,
1285 buf,
1286 0);
1287 des_ecb_crypt(&ctx->key1,
1288 buf,
1289 output+offset,
1290 1);
1291 for (i = 0; i < 8; i++)
1292 output[offset + i] ^= link[i];
1293 memcpy(link, data + offset, 8);
1294 offset+=8;
1295 }
1296 *outlen = len;
1297 if(offset<len) {
1298 *outlen += len - offset;
1299 tmp = offset;
1300 memset(buf, 0, 8);
1301 i = 0;
1302 while(tmp<len) {
1303 buf[i++] = data[tmp];
1304 tmp++;
1305 }
1306 des_ecb_crypt(&ctx->key3,
1307 buf,
1308 output+offset,
1309 1);
1310 des_ecb_crypt(&ctx->key2,
1311 output+offset,
1312 buf,
1313 0);
1314 des_ecb_crypt(&ctx->key1,
1315 buf,
1316 output+offset,
1317 1);
1318 for (i = 0; i < 8; i++)
1319 output[offset + i] ^= link[i];
1320 }
1321 return 0;
1322 }
1323
1324 static gint
1325 des3_decrypt(PurpleCipherContext *context, const guchar data[],
1326 size_t len, guchar output[], size_t *outlen)
1327 {
1328 struct _des3_ctx *ctx = purple_cipher_context_get_data(context);
1329
1330 if (ctx->mode == PURPLE_CIPHER_BATCH_MODE_ECB) {
1331 return des3_ecb_decrypt(ctx, data, len, output, outlen);
1332 } else if (ctx->mode == PURPLE_CIPHER_BATCH_MODE_CBC) {
1333 return des3_cbc_decrypt(ctx, data, len, output, outlen);
1334 } else {
1335 g_return_val_if_reached(0);
1336 }
1337
1338 return 0;
1339 }
1340
1341 static void
1342 des3_set_batch(PurpleCipherContext *context, PurpleCipherBatchMode mode)
1343 {
1344 struct _des3_ctx *ctx = purple_cipher_context_get_data(context);
1345
1346 ctx->mode = mode;
1347 }
1348
1349 static PurpleCipherBatchMode
1350 des3_get_batch(PurpleCipherContext *context)
1351 {
1352 struct _des3_ctx *ctx = purple_cipher_context_get_data(context);
1353
1354 return ctx->mode;
1355 }
1356
1357 static void
1358 des3_set_iv(PurpleCipherContext *context, guchar *iv, size_t len)
1359 {
1360 struct _des3_ctx *ctx;
1361
1362 g_return_if_fail(len == 8);
1363
1364 ctx = purple_cipher_context_get_data(context);
1365
1366 memcpy(ctx->iv, iv, len);
1367 }
1368
1369 static void
1370 des3_init(PurpleCipherContext *context, gpointer extra)
1371 {
1372 struct _des3_ctx *mctx;
1373 mctx = g_new0(struct _des3_ctx, 1);
1374 purple_cipher_context_set_data(context, mctx);
1375 }
1376
1377 static void
1378 des3_uninit(PurpleCipherContext *context)
1379 {
1380 struct _des3_ctx *des3_context;
1381
1382 des3_context = purple_cipher_context_get_data(context);
1383 memset(des3_context, 0, sizeof(des3_context));
1384
1385 g_free(des3_context);
1386 des3_context = NULL;
1387 }
1388
1389 static PurpleCipherOps DES3Ops = {
1390 NULL, /* Set option */
1391 NULL, /* Get option */
1392 des3_init, /* init */
1393 NULL, /* reset */
1394 des3_uninit, /* uninit */
1395 des3_set_iv, /* set iv */
1396 NULL, /* append */
1397 NULL, /* digest */
1398 des3_encrypt, /* encrypt */
1399 des3_decrypt, /* decrypt */
1400 NULL, /* set salt */
1401 NULL, /* get salt size */
1402 des3_set_key, /* set key */
1403 NULL, /* get key size */
1404 des3_set_batch, /* set batch mode */
1405 des3_get_batch, /* get batch mode */
1406
1407 /* padding */
1408 NULL,
1409 NULL
1410 };
1030 1411
1031 /******************************************************************************* 1412 /*******************************************************************************
1032 * SHA-1 1413 * SHA-1
1033 ******************************************************************************/ 1414 ******************************************************************************/
1034 #define SHA1_ROTL(X,n) ((((X) << (n)) | ((X) >> (32-(n)))) & 0xFFFFFFFF) 1415 #define SHA1_ROTL(X,n) ((((X) << (n)) | ((X) >> (32-(n)))) & 0xFFFFFFFF)
1264 NULL, /* decrypt */ 1645 NULL, /* decrypt */
1265 NULL, /* set salt */ 1646 NULL, /* set salt */
1266 NULL, /* get salt size */ 1647 NULL, /* get salt size */
1267 NULL, /* set key */ 1648 NULL, /* set key */
1268 NULL, /* get key size */ 1649 NULL, /* get key size */
1650 NULL, /* set batch mode */
1651 NULL, /* get batch mode */
1269 1652
1270 /* padding */ 1653 /* padding */
1271 NULL,
1272 NULL,
1273 NULL, 1654 NULL,
1274 NULL 1655 NULL
1275 }; 1656 };
1276 1657
1277 /******************************************************************************* 1658 /*******************************************************************************
1433 NULL, /* decrypt */ 1814 NULL, /* decrypt */
1434 NULL, /* set salt */ 1815 NULL, /* set salt */
1435 NULL, /* get salt size */ 1816 NULL, /* get salt size */
1436 rc4_set_key, /* set key */ 1817 rc4_set_key, /* set key */
1437 rc4_get_key_size, /* get key size */ 1818 rc4_get_key_size, /* get key size */
1819 NULL, /* set batch mode */
1820 NULL, /* get batch mode */
1438 1821
1439 /* padding */ 1822 /* padding */
1440 NULL,
1441 NULL,
1442 NULL, 1823 NULL,
1443 NULL 1824 NULL
1444 }; 1825 };
1445 1826
1446 /******************************************************************************* 1827 /*******************************************************************************
1508 caps |= PURPLE_CIPHER_CAPS_GET_SALT_SIZE; 1889 caps |= PURPLE_CIPHER_CAPS_GET_SALT_SIZE;
1509 if(ops->set_key) 1890 if(ops->set_key)
1510 caps |= PURPLE_CIPHER_CAPS_SET_KEY; 1891 caps |= PURPLE_CIPHER_CAPS_SET_KEY;
1511 if(ops->get_key_size) 1892 if(ops->get_key_size)
1512 caps |= PURPLE_CIPHER_CAPS_GET_KEY_SIZE; 1893 caps |= PURPLE_CIPHER_CAPS_GET_KEY_SIZE;
1894 if(ops->set_batch_mode)
1895 caps |= PURPLE_CIPHER_CAPS_SET_BATCH_MODE;
1896 if(ops->get_batch_mode)
1897 caps |= PURPLE_CIPHER_CAPS_GET_BATCH_MODE;
1513 1898
1514 return caps; 1899 return caps;
1515 } 1900 }
1516 1901
1517 gboolean 1902 gboolean
1635 2020
1636 purple_ciphers_register_cipher("md5", &MD5Ops); 2021 purple_ciphers_register_cipher("md5", &MD5Ops);
1637 purple_ciphers_register_cipher("sha1", &SHA1Ops); 2022 purple_ciphers_register_cipher("sha1", &SHA1Ops);
1638 purple_ciphers_register_cipher("md4", &MD4Ops); 2023 purple_ciphers_register_cipher("md4", &MD4Ops);
1639 purple_ciphers_register_cipher("des", &DESOps); 2024 purple_ciphers_register_cipher("des", &DESOps);
2025 purple_ciphers_register_cipher("des3", &DES3Ops);
1640 purple_ciphers_register_cipher("rc4", &RC4Ops); 2026 purple_ciphers_register_cipher("rc4", &RC4Ops);
1641 } 2027 }
1642 2028
1643 void 2029 void
1644 purple_ciphers_uninit() { 2030 purple_ciphers_uninit() {
1960 return cipher->ops->get_key_size(context); 2346 return cipher->ops->get_key_size(context);
1961 else { 2347 else {
1962 purple_debug_info("cipher", "the %s cipher does not support the " 2348 purple_debug_info("cipher", "the %s cipher does not support the "
1963 "get_key_size operation\n", cipher->name); 2349 "get_key_size operation\n", cipher->name);
1964 2350
2351 return -1;
2352 }
2353 }
2354
2355 void
2356 purple_cipher_context_set_batch_mode(PurpleCipherContext *context,
2357 PurpleCipherBatchMode mode)
2358 {
2359 PurpleCipher *cipher = NULL;
2360
2361 g_return_if_fail(context);
2362
2363 cipher = context->cipher;
2364 g_return_if_fail(cipher);
2365
2366 if(cipher->ops && cipher->ops->set_batch_mode)
2367 cipher->ops->set_batch_mode(context, mode);
2368 else
2369 purple_debug_info("cipher", "The %s cipher does not support the "
2370 "set_batch_mode operation\n", cipher->name);
2371 }
2372
2373 PurpleCipherBatchMode
2374 purple_cipher_context_get_batch_mode(PurpleCipherContext *context)
2375 {
2376 PurpleCipher *cipher = NULL;
2377
2378 g_return_val_if_fail(context, -1);
2379
2380 cipher = context->cipher;
2381 g_return_val_if_fail(cipher, -1);
2382
2383 if(cipher->ops && cipher->ops->get_batch_mode)
2384 return cipher->ops->get_batch_mode(context);
2385 else {
2386 purple_debug_info("cipher", "The %s cipher does not support the "
2387 "get_batch_mode operation\n", cipher->name);
1965 return -1; 2388 return -1;
1966 } 2389 }
1967 } 2390 }
1968 2391
1969 void 2392 void