113 lines
2.1 KiB
C
113 lines
2.1 KiB
C
#include "rsa.h"
|
|
#include "rand.h"
|
|
#include <stdbool.h>
|
|
#include <stdint.h>
|
|
|
|
int gcd(int a, int b) {
|
|
while (b != 0) {
|
|
int temp = b;
|
|
b = a % b;
|
|
a = temp;
|
|
}
|
|
|
|
return a;
|
|
}
|
|
|
|
int totient(int n) {
|
|
int result = n;
|
|
|
|
// Check for prime factors
|
|
for (int p = 2; p * p <= n; p++) {
|
|
if (n % p == 0) {
|
|
// If p is a prime factor of n, remove all occurrences of p
|
|
while (n % p == 0) {
|
|
n /= p;
|
|
}
|
|
result -= result / p;
|
|
}
|
|
}
|
|
|
|
// If n is still greater than 1, then it's a prime factor itself
|
|
if (n > 1) {
|
|
result -= result / n;
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
uint64_t modexp(uint64_t a, uint64_t b, uint64_t m) {
|
|
uint64_t result = 1;
|
|
a = a % m; // In case a is greater than m
|
|
|
|
while (b > 0) {
|
|
// If b is odd, multiply a with result
|
|
if (b % 2 == 1)
|
|
result = (result * a) % m;
|
|
|
|
// b must be even now
|
|
b = b >> 1; // b = b // 2
|
|
a = (a * a) % m; // Change a to a^2
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
uint64_t gen_prime(uint64_t min, uint64_t max) {
|
|
uint64_t cand = 0;
|
|
while (!miller_rabin(cand, 10)) cand = prand_range(min, max);
|
|
|
|
return cand;
|
|
}
|
|
|
|
bool is_prime(int n) {
|
|
if (n < 2)
|
|
return false;
|
|
|
|
for (int i = 2; i < n / 2 + 1; i++) {
|
|
if (n % i == 0)
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
bool miller_rabin(int n, int k) {
|
|
if (n < 2)
|
|
return false;
|
|
|
|
int d = n - 1;
|
|
int s = 0;
|
|
|
|
while (d % 2 == 0) {
|
|
d /= 2;
|
|
s++;
|
|
}
|
|
|
|
for (int i = 0; i < k; i++) {
|
|
int a = prand_range(2, n - 2);
|
|
int x = modexp(a, d, n);
|
|
|
|
if (x == 1 || x == n - 1)
|
|
continue;
|
|
|
|
for (int r = 1; r < s; r++) {
|
|
x = modexp(x, 2, n);
|
|
if (x == n - 1)
|
|
break;
|
|
}
|
|
|
|
if (x != n - 1)
|
|
return false; // Not prime
|
|
}
|
|
|
|
return true; // Likely prime
|
|
}
|
|
|
|
int mod_inverse(int e, int phi) {
|
|
for (int d = 0; d < phi; d++) {
|
|
if ((d * e) % phi == 1)
|
|
return d;
|
|
}
|
|
|
|
return 0;
|
|
}
|