Чтение файла, шифрование Blowfish - C (СИ)
Формулировка задачи:
Помогите пожалуйста, очень срочно.
Моя задача реализовать алгоритм шифрования Blowfish. Шифрование файлов/папок.
В переменные high, low подаётся информация по 32 бита (4 байта), я понимаю, что в чём проблема взять ф-цию fread и считывать, но как правильно это сделать, т.к. если у нас в конце получается остается меньше 4 байт информации мы должны заполнить недостающее место НУЛЯМИ, или другим заранее известным способом.
Помогите реализовать функцию которая к примеру будет открывать файл и считывать в эти переменные 4 байта.
И ещё один вопрос, я хочу зашифровать каталог с файлами и подкаталогами, всё это делаю при помощи FindFirstFile, FindNextFile (это я знаю), по идее я должен зашифрованный вариант записать в один файл, но как при расшифровки восстановить каталоги, подскажите.
в строке unsigned long high = 1, low = 6556; это пример шифрования значений 1 и 6556
#include <locale.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <windows.h>
typedef struct _blowfish_ctx
{
unsigned long P[18];
unsigned long sbox[4][256];
}blowfish_ctx;
//Матрица подстановки
const unsigned int FIXED_S[4][256] = {
{0xD1310BA6, 0x98DFB5AC, 0x2FFD72DB, 0xD01ADFB7,
0xB8E1AFED, 0x6A267E96, 0xBA7C9045, 0xF12C7F99,
//....256 пропустил для экономии места
0x1948C25C, 0x02FB8A8C, 0x01C36AE4, 0xD6EBE1F9,
0x90D4F869, 0xA65CDEA0, 0x3F09252D, 0xC208E69F,
0xB74E6132, 0xCE77E25B, 0x578FDFE3, 0x3AC372E6}
};
//Ключи шифрования
const unsigned long FIXED_P[] = {
0x243F6A88, 0x85A308D3, 0x13198A2E, 0x03707344,
0xA4093822, 0x299F31D0, 0x082EFA98, 0xEC4E6C89,
0x452821E6, 0x38D01377, 0xBE5466CF, 0x34E90C6C,
0xC0AC29B7, 0xC97C50DD, 0x3F84D5B5, 0xB5470917,
0x9216D5D9, 0x8979FB1B};
void swap(unsigned long *a, unsigned long *b)
{
unsigned long temp;
if(a && b)
temp = *a, *a = *b, *b = temp;
}
//Функция F(x)
unsigned long F(blowfish_ctx *S, unsigned long x)
{
return ((S->sbox[0][(x >> 24) & 0xFF] + S->sbox[1][(x >> 16) & 0xFF]) ^ S->sbox[2][(x >> 8) & 0xFF]) + S->sbox[3][(x) & 0xFF];
}
//Дешифрование
void blowfish_decrypt_block(blowfish_ctx *ctx, unsigned long *high, unsigned long *low)
{
int i;
for(i = 17; i > 1; i--)
{
*high ^= ctx->P[i];
*low ^= F(ctx, *high);
swap(low, high);
}
swap(low, high);
*high ^= ctx->P[0];
*low ^= ctx->P[1];
}
//Шифрование
void blowfish_encrypt_block(blowfish_ctx *ctx, unsigned long *high, unsigned long *low)//high,low -
{ //левый и правый блоки
int i;
for(i = 0; i < 16; i++) //шифрование 16 раундов
{
*high ^= ctx->P[i]; //XOR-им high с кючами P[i]
*low ^= F(ctx, *high); //XOR low и F(x)
swap(low, high); //Меняем местами
}
swap(low, high);
*low ^= ctx->P[16]; //17-й
*high ^= ctx->P[17]; //и 18-й ключ XOR-ся с выходными блоками последнего раунда
}
int blowfish_init(blowfish_ctx *ctx, unsigned char *key, size_t key_len)
{
int i, j;
unsigned long k, l;
unsigned long long_key;
if(ctx && key && key_len > 0 && key_len <= 56)
{
memcpy(ctx->P, FIXED_P, 18 * sizeof(FIXED_P));
for(i = 0; i < 4; i++)
memcpy(ctx->sbox[i], FIXED_S[i], sizeof(FIXED_S[i]));
for(i = 0, k = 0; i < 18; i++)
{
for(j = 0, long_key = 0; j < 4; j++, k++)
long_key = (long_key << 8) | key[k % key_len];
ctx->P[i] ^= long_key;
}
for(i = 0, k = 0, l = 0; i < 18; i++)
{
blowfish_encrypt_block(ctx, &k, &l);
ctx->P[i] = k;
ctx->P[++i] = l;
}
for(i = 0; i < 4; i++)
{
for(j = 0; j < 256; j++)
{
blowfish_encrypt_block(ctx, &k, &l);
ctx->sbox[i][j] = k;
ctx->sbox[i][++j] = l;
}
}
return 0;
}
return -1;
}
int SeachFile(char *file)
{
char buffer[5] = "";
FILE *f = fopen(file, "r");
if(f == NULL)
return 0;
while(feof(f) == 0)
{
fread(&buffer, 4, 1, f);
printf("%s", buffer);
fread(&buffer, 4, 1, f);
printf("%s", buffer);
}
return 1;
}
int main(int argc, char **argv)
{
setlocale(LC_ALL, "RU");
blowfish_ctx *ctx = (blowfish_ctx *)malloc(sizeof(blowfish_ctx));
unsigned long high = 1, low = 6556;
if(!ctx)
{
puts("Insufficient memory allocated");
return -1;
}
if(blowfish_init(ctx, (unsigned char *)"TESTKEY", 7) != 0)
{
free(ctx);
puts("Key initialization failed");
return -1;
}
SeachFile("blowfish.obj");
blowfish_encrypt_block(ctx, &high, &low);
printf("Шифрование: Верхний 32 bits:%08X Нижний 32 bits:%08X\n", high, low);
blowfish_decrypt_block(ctx, &high, &low);
printf("Дешифрование: Верхний 32 bits:%08X Нижний 32 bits:%08X\n", high, low);
free(ctx);
return 0;
}Решение задачи: «Чтение файла, шифрование Blowfish»
textual
Листинг программы
blowfish_decrypt_block(ctx, &high, &low);//расшифровываю fprintf(f2, "%08x%08x", high, low); //записываю в файл
Объяснение кода листинга программы
blowfish_decrypt_block(ctx, &high, &low);- выполняется операция расшифровки блоков данных с использованием алгоритма Blowfish.fprintf(f2,%08x%08x, high, low);- выполняется запись в файл значения двух переменных, которые были получены после расшифровки.