Skip to content

Instantly share code, notes, and snippets.

@nbaksalyar
Created March 7, 2014 10:00
Show Gist options
  • Save nbaksalyar/9408795 to your computer and use it in GitHub Desktop.
Save nbaksalyar/9408795 to your computer and use it in GitHub Desktop.
/* Polyalphabetic encryption - Enigma-like. */
#include <stdio.h>
#include <string.h>
char *alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
unsigned long rand = 42;
#define RNG_M 4294967296
#define RNG_C 12345
#define RNG_A 1103515245
unsigned long rng() {
rand = (rand * RNG_A + RNG_C) % RNG_M;
return rand;
}
void gen_table(char *dst, char *src) {
int iteration = 0;
unsigned char g, uniq[36];
memset(&uniq[0], 0, 36);
while (iteration < 36) {
g = rng() % 36;
if (uniq[g] == 0) {
if (src != 0)
src[iteration] = g;
if (dst != 0)
dst[g] = iteration;
uniq[g] = 1;
iteration++;
}
}
}
void gen_encypher_table(char *t) {
gen_table(&t[0], 0L);
}
void gen_decypher_table(char *t) {
gen_table(0L, &t[0]);
}
void cypher(char *p, int r, void (*table_fn)(char *)) {
char buffer[36];
int val;
rand = r;
while (*p) {
table_fn(&buffer[0]);
if (*p >= 'A' && *p <= 'Z') {
val = *p - 'A';
} else if (*p >= '0' && *p <= '9') {
val = 26 + (*p - '0');
}
*p = alphabet[buffer[val]];
++p;
}
}
void test_gen_table() {
int i, j;
char buffer[36];
for (i = 0; i < 30; i++) {
gen_table(&buffer[0], 0L);
for (j = 0; j < 36; j++) {
putchar(alphabet[buffer[j]]);
}
putchar('\n');
}
}
int main(int argc, char **argv) {
int r, s;
char *plaintext;
char mode;
void (*table)(char *);
if (argc < 3) {
printf("usage: polyalphabetic [mode - e/d] [plaintext] [starting rotor position]");
return 0;
}
mode = *argv[1];
plaintext = argv[2];
sscanf(argv[3], "%d", &r); /* rotor starting position */
if (mode == 'e')
table = gen_encypher_table;
else
table = gen_decypher_table;
cypher(plaintext, r, table);
printf(plaintext);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment