Advertisement
leomaster

Ciphers

Jun 26th, 2018
224
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 6.06 KB | None | 0 0
  1. #include <stdio.h>
  2. #include <string.h>
  3.  
  4. #define BUFLEN 1024
  5. #define ALPHABET_LETTER_COUNT 26
  6. #define ENGLISH_FREQUENCIES ETAOINSRHDLUCMFYWGPBVKXQJZ
  7. #define STR_END '\0'
  8.  
  9. /* Buffer pou apothikeyei tin isodo prosorina gia na ektelestoun oi algorithmoi */
  10. int buf[BUFLEN];
  11.  
  12. void printhelp() {
  13.         puts (
  14.             "       [ Decipher ] -- by -- [ /fb.me/masterleo ]      \n"
  15.             "         == || ==                  == || ==            \n"
  16.             " ||==================================================||\n"
  17.             " || Execute with one of the following arguments      ||\n"
  18.             " ||                                                  ||\n"
  19.             " || -c for caesar                                    ||\n"
  20.             " || -a for affine                                    ||\n"
  21.             " || -s for subtitution                               ||\n"
  22.             " || -t for transposition                             ||\n"
  23.             " || -v for vigenere                                  ||\n"
  24.             " ||                                                  ||\n"
  25.             " || TIP: Redirect std streams for comfort            ||\n"
  26.             " || Example usage: ./cipher -a < finput > foutput    ||\n"
  27.             " ||==================================================||\n"
  28.         );
  29. }
  30.  
  31. /* sinartisi ipologismou tou a^-1 gia to affine cipher */
  32. inline int modinverse(int a, int m) {
  33.     int x;
  34.     for(a%=m,x=1;x<m;++x)
  35.         if (a*x%m==1)
  36.             return x;
  37. }
  38.  
  39. /* sinartisi mod pou ipostirizi arnitikous */
  40. inline int mod(int a, int b) {
  41.     return a%b<0?a%b+b:a%b;
  42. }
  43.  
  44. /* epistrefei 'A' i 'a' analoga an to orisma ine kefaleo i mikro */
  45. inline int aA(int c) {
  46.     return isupper(c)?'A':'a';
  47. }
  48.  
  49. /* ipologizei ton megisto kino diereti dio arithmon */
  50. inline int gcd(int a, int b) {
  51.     return a?gcd(b%a,a):b;
  52. }
  53.  
  54. inline void printtitle(char *s) {
  55.     printf("= [ %s cipher ] =\n==================================================\n\n",s);
  56. }
  57.  
  58. void caesar() {
  59.     printtitle("Caesar");
  60.  
  61.     int k=ALPHABET_LETTER_COUNT,*p=buf;
  62.    
  63.     /* diavazoume to minima ston buffer */
  64.     while (~(*p++=getchar()) || ++*--p);
  65.  
  66.     /* efarmozoume caesar diatrexontas ton buffer gia oles tis pithanes periptoseis tou k */
  67.     while (k--) {
  68.  
  69.         printf("- [ k=%d ] -\n",ALPHABET_LETTER_COUNT-k);
  70.  
  71.         /* diatrexo tous xaraktires tou buffer */
  72.         for (p=buf;*p;putchar(*p++))
  73.  
  74.             /* an o xaraktiras ine grama */
  75.             if (isalpha(*p))
  76.  
  77.                 /* efarmozo caesar shift */
  78.                 *p = (*p-aA(*p)+1)%ALPHABET_LETTER_COUNT + aA(*p);
  79.  
  80.         puts("--------------------------------------------------\n");
  81.     }
  82.  
  83. }
  84.  
  85. void affine() {
  86.     printtitle("Affine");
  87.  
  88.     int a,ainv,b,count=0,*p=buf;
  89.  
  90.     /* diavazoume to minima ston buffer */
  91.     while (~(*p++=getchar()) || ++*--p);
  92.        
  93.     /* gia kathe a apo 1 eos arithmo gramaton alfavitou */
  94.     for (a=1;a<ALPHABET_LETTER_COUNT;++a) {
  95.  
  96.         /* an o a ke o arithmos gramaton alfavitou ine protoi metaksi tous tote */
  97.         if (gcd(ALPHABET_LETTER_COUNT,a)==1) {
  98.  
  99.             /* ipologizoume ton a^-1 */
  100.             ainv = modinverse(a,ALPHABET_LETTER_COUNT);
  101.  
  102.             /* gia kathe b apo 0 eos arithmo gramaton alfavitou */
  103.             for (b=0;b<ALPHABET_LETTER_COUNT;++b) {
  104.  
  105.                 printf("- [ count=%d, a=%d, ainv=%d, b=%d ] -\n",++count,a,ainv,b);
  106.  
  107.                 /* diatrexo tous xaraktires tou buffer */
  108.                 for (p=buf;*p;p++)
  109.  
  110.                     /* an o xaraktiras ine grama */
  111.                     if (isalpha(*p))
  112.  
  113.                         /* efarmozo ton tipo apokriptografisis tou affine cipher */
  114.                         putchar(mod(ainv*((*p)-aA(*p)-b),ALPHABET_LETTER_COUNT)+aA(*p));
  115.  
  116.                     else
  117.  
  118.                         /* alios apla ektipono ton xaraktira */
  119.                         putchar(*p);
  120.                 puts("--------------------------------------------------\n");
  121.             }
  122.         }
  123.  
  124.     }
  125.    
  126. }
  127.  
  128. /* domi dedomenon pou periexi ta statistika stixia ton gramaton */
  129. struct letter {
  130.     int frequency;
  131.     double percent;
  132.     int character;
  133. } substitutes[ALPHABET_LETTER_COUNT];
  134.  
  135. /* sinartisi gia tin sigkrisi 2 sixnotiton pou xrisimopiiete apo tin qsort */
  136. int compare(const void * a, const void * b) {
  137.     return ((struct letter *)b)->frequency-((struct letter *)a)->frequency;
  138. }
  139.  
  140. void substitution() {
  141.     printtitle("Substitution");
  142.  
  143.     int letter_count=0,*p=buf,i;
  144.  
  145.     char *eng_freq = "ETAOINSRHDLUCMFYWGPBVKXQJZ";
  146.  
  147.     /* diavazoume to minima ston buffer ke afxanoume tin antistixi thesi tou pinaka sixnotiton kata 1 */
  148.     while (~(*p++=getchar()) || ++*--p);
  149.  
  150.         /* an o xaraktiras ine grama tote */
  151.         if (isalpha(*(--p)))
  152.  
  153.             /* afxanoume tin antistixi thesi tou pinaka sixnotiton */
  154.             ++(substitutes[(*p)-aA(*p++)].frequency), letter_count++;
  155.  
  156.         else
  157.  
  158.             ++p;
  159.  
  160.     /* enimeronoume tin domi ton statistikon ipologizontas ta pososta */
  161.     for (i=0;i<ALPHABET_LETTER_COUNT;++i) {
  162.         substitutes[i].character=i+'A';
  163.         substitutes[i].percent= (100*(double)substitutes[i].frequency/(double)letter_count);
  164.     }
  165.  
  166.     /* taksinomoume ton pinaka me basi tis sixnotites emfanisis */
  167.     qsort (substitutes, ALPHABET_LETTER_COUNT, sizeof(struct letter), compare);
  168.  
  169.     /* ektiponoume ta apotelesmata ton statistikon stixion */
  170.     puts("- Substitute array is now sorted! -\n--------------------------------------------------\n| Chr | ## |   %   | Eng |\n--------------------------");
  171.     for (i=0;i<ALPHABET_LETTER_COUNT;++i)
  172.         printf("|  %c  | %2d | %5.2f |  %c  |\n",substitutes[i].character,substitutes[i].frequency,substitutes[i].percent,eng_freq[i]);
  173.     puts("--------------------------\n\n- Possible message -\n--------------------------------------------------");
  174.  
  175.     /* ektiponoume to apokriptografimeno minima */
  176.     for (p=buf;*p;++p)
  177.         if (!isalpha(*p))
  178.             putchar(*p);
  179.         else
  180.             for (i=0;;++i)
  181.                 if (substitutes[i].character==(*p)) {
  182.                     putchar(eng_freq[i]);
  183.                     break;
  184.                 }
  185.    
  186.  
  187. }
  188.  
  189. int main(int argc, char *argv[]) {
  190.  
  191.     if (argc>1) {
  192.         if (0) {
  193.         /* Caesar */
  194.         } else if (!strcmp("-c",argv[1])) {
  195.             caesar();
  196.         /* Affine */
  197.         } else if (!strcmp("-a",argv[1])) {
  198.             affine();
  199.         /* Subtitution */
  200.         } else if (!strcmp("-s",argv[1])) {
  201.             substitution();
  202.         /* Help */
  203.         } else if (!strcmp("-h",argv[1])) {
  204.             printhelp();
  205.         /* Error */
  206.         } else {
  207.             puts("Error: Invalid flag");
  208.             printhelp();
  209.         }
  210.     } else {
  211.         printhelp();
  212.  
  213.         int i,t;
  214.         for (i=-5;i<=10;i++) {
  215.             if(i==0) continue;
  216.         t=i;
  217.         t+=(t%t);
  218.         printf("i:%d t:%d\n",i,t);
  219.         }
  220.     }
  221.    
  222.     return 0;
  223. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement