Finished project

This commit is contained in:
2025-02-10 13:25:07 +00:00
parent 39e4e9ce0c
commit d4eef99b2e
2 changed files with 619 additions and 0 deletions

573
main.cpp Normal file
View File

@@ -0,0 +1,573 @@
#include <cstdlib>
# include<iostream>
# include<string>
# include<random>
# include<cmath>
# include<array>
using namespace std;
typedef long long int Lint; // 64 bits
typedef double Ldouble;
struct security {
int num_shares;
int num_required;
};
struct shareStruct {
Lint y;
int x;
};
bool isPrime(Lint n) {
int flag = 0;
for (int i = 2; i <= n / i; ++i) {
if (n % i == 0) {
flag = 1;
break;
}
}
if (flag == 0) return true;
else return false;
}
Lint genRandInt(int n) {
// Returns a random number
// between 2**(n-1)+1 and 2**n-1
//long max = (long)powl(2, n) - 1;
//long min = (long)powl(2, n - 1) + 1;
long max = (long)pow(2, n) - 1;
long min = (long)pow(2, n - 1) + 1;
Lint result = min + (rand() % ( max - min + 1 ) );
//cout << "Random num: " << result << endl;
return result;
}
Lint genPrime() {
Lint prime = 10;
while (isPrime(prime) == false) {
int complexity = 50;
prime = genRandInt(complexity);
}
return prime;
}
Lint getSecret() {
int secret;
Lint total = 1;
string total_string = "";
string secret_text;
cout << "Enter share secret:";
cin.ignore();
getline(cin, secret_text);
cout << endl;
for (int i=0; i < size(secret_text); i++) {
char character = secret_text[i];
string character_value = to_string(int(character));
int append_size = 3 - size(character_value);
string append_string = "";
for (int i=0; i<append_size; i++) {
cout << "in for" << endl;
append_string = append_string + "0";
}
character_value = append_string + character_value;
total_string = total_string + character_value;
}
cout << "total string: " << total_string << endl;
secret = total;
return secret;
}
int* encodeSecret(int* poly, const int secret, const int num_required) {
poly[num_required-1] = secret;
return poly;
}
security getSecurity() {
int num_shares = 0;
int num_required = 1;
while ((num_required > num_shares) and (num_required < 7)) {
cout << "Enter the number of shares required (2-6): ";
cin >> num_required;
cout << endl << "Enter the number of shares to be created: ";
cin >> num_shares;
cout << endl;
}
security securityOptions;
securityOptions.num_shares = num_shares;
securityOptions.num_required = num_required;
return securityOptions;
}
Lint getPolyY(const int* poly, int poly_len, int poly_x, const Lint prime) {
Lint total = 0;
Lint poly_y = 0;
for (int i=0; i<poly_len+1; i++) {
int power = poly_len - i;
int coefficient = poly[i];
poly_y = coefficient * pow(poly_x, power);
total = total + poly_y;
//cout << endl << "--- next share ---" << endl;
//cout << "In getPolyY: total: " << total << endl;
//cout << "In getPolyY: poly_y: " << poly_y << endl;
//cout << "In getPolyY: power: " << power << endl;
//cout << "In getPolyY: pow(poly_x, power): " << pow(poly_x, power) << endl;
//cout << "In getPolyY: poly_x: " << poly_x << endl;
//cout << "In getPolyY: coefficient: " << coefficient << endl;
//cout << endl;
}
return total;
}
shareStruct* genShares(int num_shares, int num_required, const int* poly, const Lint prime){
shareStruct* shares = new shareStruct[num_shares];
for (int i=1; i<=num_shares; i++) {
shareStruct share;
share.x = i;
share.y = getPolyY(poly, num_required-1, share.x, prime);
shares[i-1] = share;
}
return shares;
}
int* genPoly(int degree, const Lint prime, const Lint secret) {
int* poly = new int[degree];
for (int i = 0; i < degree; i++) {
int random_num = genRandInt(10);
poly[i] = prime % random_num;
}
return poly;
}
void outputShares(shareStruct* shares, int num_shares) {
bool pretty = true;
cout << "Shares: " << endl;
for (int i = 0; i<num_shares; i++) {
if (pretty == false) {
cout << "(" << shares[i].x << ", " << shares[i].y << "), ";
}
else {
cout << "Share " << shares[i].x << ": " << shares[i].y << " | ";
}
}
cout << endl;
}
// RBP
void outputPoly(const int* poly, Lint secret, int poly_len) {
string cof = "";
for (int i=0; i<poly_len-1; i++) {
int power = poly_len - i - 1;
cof = cof + to_string(poly[i]) + "x^" + to_string(power) + " + ";
}
cout << "Poly: " << cof << secret << endl;
}
// RBP
void newSecret() {
cout << "----- Create a new secret -----" << endl;
security securityOptions = getSecurity();
const int num_shares = securityOptions.num_shares;
const int num_required = securityOptions.num_required;
const Lint prime = genPrime();
Lint secret = getSecret();
// RBP
secret = 520;
// RBP
int* poly = genPoly(num_required-1, prime, secret);
poly = encodeSecret(poly, secret, num_required);
shareStruct* shares = genShares(num_shares, num_required, poly, prime);
outputShares(shares, num_shares);
}
// solving polynomials
struct inputStruct {
int required;
shareStruct* shares;
};
inputStruct getInfo() {
inputStruct inputs;
int required;
cout << "Enter number of shares required: ";
// RBP
required = 3;
// RBP
cin >> required;
cout << endl;
shareStruct* shares = new shareStruct[required];
for (int i = 0; i < required; i++) {
cout << "Enter number of next share: ";
shareStruct share;
// RBP
share.x = 1;
// RBP
cin >> share.x;
cout << "Enter the share secret: ";
// RBP
share.y = 3;
// RBP
cin >> share.y;
cout << endl;
shares[i] = share;
}
inputs.shares = shares;
inputs.required = required;
return inputs;
}
struct polyTerm {
Lint coefficient;
int power;
};
struct linearEquation {
shareStruct point;
polyTerm* terms;
};
linearEquation* constructEquations(const int required, shareStruct shares[]) {
linearEquation* equations = new linearEquation[required];
shareStruct share;
polyTerm term;
for (int i = 0; i < required; i++) {
share = shares[i];
linearEquation equation;
polyTerm* terms = new polyTerm[required];
for (int j = 0; j < required; j++) {
term.power = required - 1 - j;
terms[j] = term;
}
equation.terms = terms;
equation.point.x = share.x;
equation.point.y = share.y;
// RBP
//cout << "y: " << equation.point.y << endl;
//cout << "x: " << equation.point.x << endl;
//cout << "i: " << i << endl;
// RBP
equations[i] = equation;
// dont delete terms from memory as its referanced in equations
}
return equations;
}
struct matrix{
Lint** matrix;
int dimension_x;
int dimension_y;
};
struct matrix_system {
matrix A;
matrix B;
matrix X;
};
matrix_system formMatrix(const linearEquation* equations, int required) {
Lint** matrixA = new Lint*[required];
Lint** matrixB = new Lint*[required];
for (int i=0; i < required; i++) {
linearEquation equation = equations[i];
Lint* lineA = new Lint[required];
for (int j=0; j < required; j++) {
lineA[j] = pow(equation.point.x, equation.terms[j].power);
}
matrixA[i] = lineA;
Lint* lineB = new Lint[1];
lineB[0] = equation.point.y;
matrixB[i] = lineB;
}
matrix matrixA_data; matrix matrixB_data;
matrixA_data.matrix = matrixA; matrixB_data.matrix = matrixB;
matrixA_data.dimension_x = required; matrixB_data.dimension_x = 1;
matrixA_data.dimension_y = required; matrixB_data.dimension_y = required;
matrix_system matricies;
matricies.A = matrixA_data; matricies.B = matrixB_data;
return matricies;
}
Lint** findMinor(Lint** matrixA, const int dimension, const int pos_x, const int pos_y) {
Lint** matrixB = new Lint*[dimension-1];
int matrixB_pos_x = 0; int matrixB_pos_y = 0;
for (int i=0; i<dimension; i++) {
Lint* line = new Lint[dimension-1];
for (int j=0; j<dimension; j++) {
if (i != pos_y and j != pos_x) {
line[matrixB_pos_x] = matrixA[i][j];
matrixB_pos_x++;
}
}
if (matrixB_pos_x != 0) {
matrixB[matrixB_pos_y] = line;
matrixB_pos_y++;
}
else {
delete[] line;
}
matrixB_pos_x = 0;
}
return matrixB;
}
Lint findDet(Lint** matrixA, const int dimension) {
Lint det = 0;
if (dimension == 0) {
det = 1;
}
else if (dimension == 1) {
det = matrixA[0][0];
}
else if (dimension == 2) {
det = matrixA[0][0] * matrixA[1][1] - matrixA[0][1] * matrixA[1][0];
}
else {
for (int i=0; i<dimension; i++) {
// reuse form matrix? pottentially split it up into formMatrixA and formMatrixB?
Lint** matrixB = findMinor(matrixA, dimension, i, 0);
Lint matrixB_det = findDet(matrixB, dimension-1);
Lint term = matrixA[0][i] * matrixB_det;
if ((i+1)%2 == 0) {
term = 0-term;
}
det = det + term;
}
}
return det;
}
matrix formMatrixCofactors(Lint** matrixA, const int dimension) {
Lint** matrixB = new Lint*[dimension];
for (int i=0; i<dimension; i++) {
Lint* line = new Lint[dimension];
int sign = 1;
if ((i+1)%2 == 0) {
sign = -1;
}
for (int j=0; j<dimension; j++) {
Lint** minor = findMinor(matrixA, dimension, j, i);
Lint cofactor = findDet(minor, dimension-1) * sign;
sign = -sign;
line[j] = cofactor;
}
matrixB[i] = line;
}
matrix matrix_data; matrix_data.matrix = matrixB;
matrix_data.dimension_x = dimension; matrix_data.dimension_y = dimension;
return matrix_data;
}
matrix transposeMatrix(Lint** cofactors, const int dimension) {
Lint** matrixB = new Lint*[dimension];
for (int i=0; i<dimension; i++) {
Lint* line = new Lint[dimension];
for (int j=0; j<dimension; j++) {
line[j] = cofactors[j][i];
}
matrixB[i] = line;
}
matrix matrixB_data; matrixB_data.matrix = matrixB;
matrixB_data.dimension_x = dimension; matrixB_data.dimension_y = dimension;
return matrixB_data;
}
struct float_matrix{
Ldouble** matrix;
int dimension_x;
int dimension_y;
};
struct float_matrix_system {
matrix A;
matrix B;
matrix X;
};
float_matrix multiplyConstant(matrix matrixA_data, const int dimension, const Lint det) {
Ldouble** matrixB = new Ldouble*[dimension];
Lint** matrixA = matrixA_data.matrix;
for (int i=0; i<dimension; i++) {
Ldouble* line = new Ldouble[dimension];
for (int j=0; j<dimension; j++) {
line[j] = (1.0/det) * matrixA[i][j];
}
matrixB[i] = line;
}
float_matrix matrixB_data; matrixB_data.matrix = matrixB;
matrixB_data.dimension_x = matrixA_data.dimension_x; matrixB_data.dimension_y = matrixA_data.dimension_y;
return matrixB_data;
}
float_matrix multiplyMatricies(float_matrix inverseA_data, matrix matrixB_data) {
int dimension_x = inverseA_data.dimension_x;
int dimension_y = inverseA_data.dimension_y;
Ldouble** matrixC = new Ldouble*[matrixB_data.dimension_y];
Ldouble** inverseA = inverseA_data.matrix;
Lint** matrixB = matrixB_data.matrix;
for (int i=0; i<dimension_y; i++) {
Ldouble* line = new Ldouble[0];
Ldouble result = 0;
for (int j=0; j<dimension_x; j++) {
result = result + inverseA[i][j] * matrixB[j][0];
}
line[0] = result;
matrixC[i] = line;
}
float_matrix matrixC_data; matrixC_data.matrix = matrixC;
matrixC_data.dimension_x = matrixB_data.dimension_x; matrixC_data.dimension_y = matrixB_data.dimension_y;
return matrixC_data;
}
void solve() {
cout << "----- Get secrect -----" << endl;
inputStruct inputs = getInfo();
linearEquation* equations = new linearEquation[inputs.required];
equations = constructEquations(inputs.required, inputs.shares);
matrix_system matricies = formMatrix(equations, inputs.required);
delete[] equations;
Lint det = findDet(matricies.A.matrix, matricies.A.dimension_x);
matrix cofactors = formMatrixCofactors(matricies.A.matrix, matricies.A.dimension_x);
matrix transposition = transposeMatrix(cofactors.matrix, cofactors.dimension_x);
float_matrix inverseA = multiplyConstant(transposition, transposition.dimension_x, det);
float_matrix matrixC = multiplyMatricies(inverseA, matricies.B);
Lint secret = matrixC.matrix[matrixC.dimension_y-1][0];
string display;
cout << "Type 'show me' to see the secret, anyother input will cancel the process: ";
cin.ignore(); getline(cin, display);
if (display == "show me") {
cout << "The secrect is: " << secret << endl;
}
else {
cout << "Cancelled: clearing memory..."; cout << " done" << endl;
}
cout << endl;
}
void outputMenu() {
cout << "--- Menu ---" << endl;
string items[4] = {"Get secret", "Create new secret", "Test", "Exit"};
for (int i = 0; i<(sizeof(items)/32); i++) {
int opt_num = i+1;
if (items[i] == "Exit") {
int opt_num = 99;
}
cout << opt_num << ". " << items[i] << endl;
}
cout << endl << "select your option by inputting its corresponding letter: ";
}
void solveInternal(shareStruct* shares, int required) {
inputStruct inputs;
inputs.shares = shares;
inputs.required = required;
linearEquation* equations = new linearEquation[inputs.required];
equations = constructEquations(inputs.required, inputs.shares);
matrix_system matricies = formMatrix(equations, inputs.required);
delete[] equations;
Lint det = findDet(matricies.A.matrix, matricies.A.dimension_x);
matrix cofactors = formMatrixCofactors(matricies.A.matrix, matricies.A.dimension_x);
matrix transposition = transposeMatrix(cofactors.matrix, cofactors.dimension_x);
float_matrix inverseA = multiplyConstant(transposition, transposition.dimension_x, det);
float_matrix matrixC = multiplyMatricies(inverseA, matricies.B);
Lint secret = matrixC.matrix[matrixC.dimension_y-1][0];
cout << "The secrect is: " << secret << endl << endl;
}
void newSecretInternal(const int num_shares, const int num_required) {
const Lint prime = genPrime();
Lint secret = 538;
int* poly = genPoly(num_required-1, prime, secret);
poly = encodeSecret(poly, secret, num_required);
shareStruct* shares = genShares(num_shares, num_required, poly, prime);
outputShares(shares, num_shares);
solveInternal(shares, num_required);
outputPoly(poly, secret, num_required);
}
void internalTest() {
newSecretInternal(8, 6);
newSecretInternal(12, 6);
newSecretInternal(12, 6);
}
int main() {
bool exit = false;
int selection;
while (exit == false) {
outputMenu();
cin >> selection;
cout << endl;
if (selection == 1) {
solve();
}
else if (selection == 2) {
newSecret();
}
else if (selection == 3) {
internalTest();
}
else {
exit = true;
}
}
return 0;
}

46
versions/001/old.cpp Normal file
View File

@@ -0,0 +1,46 @@
# include<iostream>
# include<string>
# include<random>
# include<cmath>
using namespace std;
int genRandInt(int range_start, int range_end) {
random_device dev;
mt19937 rng(dev());
uniform_int_distribution<mt19937::result_type> dist6(range_start, range_end);
return dist6(rng);
}
int genPolyPoints(int poly_func) {
}
int genPoly(int degree) {
int poly[degree+1];
for (int i = 0; i < degree+1; i++) {
int random_num = genRandInt(1, 99999999999999999);
poly[i] = random_num;
}
return poly;
}
void genSecret(string secret, int shares, int required=shares) {
int poly_degree = required - 1;
int poly_func = genPoly(poly_degree);
int points = genPolyPoints(poly_func)
}
void getShares(int num_shares) {
string shares[num_shares];
cout << "Enter share secret:\n"
cin >> share;
cout << "\n"
}
void encodeSecret(string secret) {
}
int main() {
return 0;
}