O procedimento keygen gera chaves RSA com base nos três números primos que lhe são passados. O seu trabalho segue o seguinte algoritmo:
#include "cyphernet.h"
typedef struct rsa_key
{
struct rsa_key_item public_key;
struct rsa_key_item private_key;
} RSAKEY;
RSAKEY local_rsa_key;
int value_is_negative(signed char *value)
{
return (*(value + VALUE_LENTH - 1) == MAX_DIGIT);
}
void dec_value(signed char *operand)
{
int i;
*operand -= 1;
for (i = 0; i < VALUE_LENTH; i++)
if (*(operand + i) < 0)
{
*(operand + i) += RADIX;
if ((i + 1) < VALUE_LENTH) *(operand + i + 1) -= 1;
}
}
void value_add(signed char *operand1, signed char *operand2)
{ //operand1 += operand2
int i;
for (i = 0; i < VALUE_LENTH; i++)
{
*(operand1 + i) += *(operand2 + i);
if (*(operand1 + i) > MAX_DIGIT)
{
*(operand1 + i) -= RADIX;
if ((i + 1) < VALUE_LENTH) *(operand1 + i + 1) += 1;
}
}
}
void div_value(signed char *dividend, signed char *divider, signed char *result, signed char *remainder)
{ //result = dividend / divider
int rl, dl;
signed char factor[VALUE_LENTH], tractor[VALUE_LENTH];
clear_value(result);
copy_value(dividend, remainder);
while (cmp_value(divider, remainder) != 1)
{
rl = get_value_lenth(remainder);
dl = get_value_lenth(divider);
if (rl == dl)
{
while (cmp_value(divider, remainder) != 1)
{
value_sub(remainder, divider);
inc_value(result);
}
} else {
clear_value(factor);
inc_value(factor);
shl_value(factor, rl - dl - 1);
mul_value(divider, factor, tractor);
while (cmp_value(tractor, remainder) != 1)
{
value_sub(remainder, tractor);
value_add(result, factor);
}
}
}
}
void long_ext_gcd(signed char *a, signed char *b, signed char *result)
{
signed char r[VALUE_LENTH], s[VALUE_LENTH], t[VALUE_LENTH], old_r[VALUE_LENTH], old_s[VALUE_LENTH];
signed char quotient[VALUE_LENTH], tmp[VALUE_LENTH], tmp2[VALUE_LENTH];
copy_value(a, old_r); copy_value(b, r);
clear_value(s);
clear_value(old_s); inc_value(old_s);
clear_value(result);
clear_value(t); inc_value(t);
while (test_value(r))
{
div_value(old_r, r, quotient, tmp);
copy_value(r, old_r); copy_value(tmp, r);
mul_value(quotient, s, tmp2);
copy_value(old_s, tmp);
value_sub(tmp, tmp2);
copy_value(s, old_s);
copy_value(tmp, s);
mul_value(quotient, t, tmp2);
copy_value(result, tmp);
value_sub(tmp, tmp2);
copy_value(t, result);
copy_value(tmp, t);
}
if (value_is_negative(result)) value_add(result, a);
}
void create_rsa_key(signed char *p, signed char *q, signed char *e, signed char *n, signed char *d)
{
signed char ip[VALUE_LENTH], iq[VALUE_LENTH], fi[VALUE_LENTH];
mul_value(p, q, n);
copy_value(p, ip); copy_value(q, iq);
dec_value(ip); dec_value(iq);
mul_value(ip, iq, fi);
long_ext_gcd(fi, e, d);
}
RSAKEY *make_rsa_key(signed char *p, signed char *q, signed char *e)
{
copy_value(e, local_rsa_key.public_key.exponent);
create_rsa_key(p, q, e, local_rsa_key.public_key.modulus, local_rsa_key.private_key.exponent);
copy_value(local_rsa_key.public_key.modulus, local_rsa_key.private_key.modulus);
return &local_rsa_key;
}
int main (int argc, char *argv[])
{
signed char p[VALUE_LENTH], q[VALUE_LENTH], e[VALUE_LENTH], d[VALUE_LENTH], n[VALUE_LENTH];
if (argc != 4)
{
printf("Неправильно указаны параметры\n");
return 1;
}
str_to_value(argv[1], p);
str_to_value(argv[2], q);
str_to_value(argv[3], e);
make_rsa_key(p, q, e);
value_to_str(local_rsa_key.private_key.modulus, n);
value_to_str(local_rsa_key.private_key.exponent, d);
value_to_str(local_rsa_key.public_key.exponent, e);
printf("%s %s \n", n, e);
printf("%s %s \n", n, d);
return 0;
}
A geração de chaves para encriptação Extra Systems Cypher Net neste programa ocorre sem a utilização de quaisquer bibliotecas de terceiros, exclusivamente por conta própria, mas obedecendo a todas as normas RSA necessárias. O programa keygen é por nós utilizado em scripts para a criação de um kit de entrega de produtos para o consumidor.
O conteúdo desta página está também disponível em inglês, francês, alemão, espanhol, italiano, ucraniano e russo.
| © Extra Systems, 2024 |
|