Зашифровать / защитить короткую строку до длинной

Я хотел бы зашифровать / защитить входную строку в следующем формате "AB123456789000" (две буквы и 12 цифр), чтобы защищенная "версия" могла быть сохранена как длинная (число) в базе данных.

Я пробовал шифрование RC2, но оно дает мне 128 бит, который не подходит для 64 бит.

2 ответа

Кодирование в 64 бит может быть сделано довольно просто:

public static long toId(String id) {
    long numPart = Long.parseLong(id.substring(2));
    long letterPart = Long.parseLong(id.substring(0, 2), 36);

    long res = (letterPart << 40) | numPart;

    System.out.println("Ids: " + id + " -> " + res);

    return res;
}

public static void main(String[] args) {
    toId("AB123456789000");
    toId("AA000000000000");
    toId("AA999999999999");
    toId("ZZ000000000000");
    toId("ZZ999999999999");
}

Результат

Ids: AB123456789000 -> 408042270693896
Ids: AA000000000000 -> 406819302277120
Ids: AA999999999999 -> 407819302277119
Ids: ZZ000000000000 -> 1423867557969920
Ids: ZZ999999999999 -> 1424867557969919

Прежде всего у меня должна быть маленькая напыщенная речь.

  1. RC2 устарел и небезопасен (обнаружены криптографические недостатки), см. Википедию. Используйте это на свой страх и риск.
  2. Почему НЕ использовать хорошую криптографию? Вы хотите что-то безопасное, поэтому просто зашифруйте что-нибудь с помощью AES, например. Я не понимаю аргумент, что полученное шифрование имеет длину 64 бита. В Java и C# все стандартные библиотеки для шифрования работают на byte[]нет необходимости представлять его как единое целое long, Каждая система баз данных также должна сохранять двоичные двоичные объекты.

Вернемся к уменьшению размера ввода до 64 бит.

Используя ASCII, ваша 14-буквенная длинная строка будет иметь длину 14 байт (= 112), ее шифрование не будет помещаться в 64 бита без сжатия. Вы можете обмануть, сказав, что формат должен быть 2 буквы, а затем 12 цифр. Для кодирования вы взяли бы первые две буквы дословно в их представлении ASCII. Это было бы 2*8 бит = 16 бит. Затем взять 12 цифр как целое число, например 123456789000 = 0x1cbe991a08 который составляет 5 байт (= 40 бит, он помещается в long). Самое большое возможное число здесь 9999999999 который 0xe8d4a50fffТаким образом, все еще можно сохранить в 5 байтов.

В целом у нас было бы 2*8 бит + 5*8 бит = 56 бит, что достаточно мало, чтобы поместиться в один блок шифрования RC2, который является 64-битным. Вы можете установить последний байт 0x00,

Итак, вкратце, 2 байта кодированной версии вашего открытого текста будут представлять значение ASCII этих двух букв, тогда следующие 5 байтов будут числом как long,

Например,AB123456789000 будет как таковой кодироваться в 0x41421cbe991a08 ('A' = 0x41, B = 0x42, затем 123456789000 = 0x1cbe991a08). Вы можете написать функции кодирования и декодирования в Java и C# для реализации этого.

Другие вопросы по тегам