/* Given a set of consecutive characters, find a hash expression that would produce the desired symbols. Result: 'A' * 24 % 50 = '\n' 'B' * 24 % 50 = '"' 'D' * 24 % 50 = ' ' */ #include /* List of consecutive unused characters from prime_cut2.c */ static const char *kKeySets[4] = { "123", "5678", "ABCD", "wxyz", }; /* Hash function. */ static int Hash(char input, int p, int q) { return input * p % q; } /* Try hashing a set of keys to the desired symbols. */ static void TryKeySet(const char *keys) { int p, q, v, coverage; const char *k; for(p = 0; p < 1000; p++) { for(q = 1; q < 1000; q++) { coverage = 0; for(k = keys; *k; k++) { v = Hash(*k, p, q); if( v == ' ' ) coverage |= 1; if( v == '\n' ) coverage |= 2; if( v == '"' ) coverage |= 4; } if( coverage == 7 ) { printf("keys = %s, p = %d, q = %d:", keys, p, q); for(k = keys; *k; k++) printf("\t%d->%d", *k, Hash(*k, p, q)); putchar('\n'); } } } } int main(void) { int k; for(k = 0; k < 4; k++) TryKeySet(kKeySets[k]); return 0; }