fork download
  1. #include <iostream>
  2. using namespace std;
  3. /*
  4.  
  5.   This is program for Encryption and Decryption
  6.   This program uses the Simple Data Encryption Standard (SDES) Algorithm.
  7.   This Algo takes 8-bits of plaintext at a time and produces 8-bits of ciphertext.
  8.   It uses 10-bits of key for Encryption and Decryption.
  9.  
  10.   Developed by : Vivek Kumar (alldogblue@yahoo.co.in)
  11.  
  12.   Created on : 31 March 2005
  13.   Last Modified on : 10 April 2005
  14.  
  15.   Any sort of suggetions/comments are most welcome on alldogblue@yahoo.co.in
  16.  
  17. */
  18. #include<stdio.h>
  19. #include<conio.h>
  20. #include<string.h>
  21. #include<stdlib.h>
  22. #include<assert.h>
  23.  
  24. void mainmenu(int *);
  25. void menuEn(char*,char*,char*);
  26. void menuDe(char*,char*,char*);
  27. int DoEnDe(char*,char*,char*,int);
  28. class SDES
  29. {
  30. private:
  31. char KEY[11],K1[9],K2[9],IPOutput[9],InvIPOutput[9];
  32. char F1Output[9],F2Output[9];
  33.  
  34. char INPUT_BIT[9],OUTPUT_BIT[9];
  35.  
  36. public:
  37. unsigned char INPUT,OUTPUT;
  38.  
  39. SDES(char *key);
  40. ~SDES();
  41. void GenerateKeys();
  42. char *Left_Shift(char *,int );
  43. void conv_to_bits(unsigned char );
  44. void IP(char *);
  45. void InvIP(char *);
  46. void DES_Encryption(unsigned char );
  47. void DES_Decryption(unsigned char );
  48. void Function_F(char *,char *,int );
  49. char *EX_OR(char *,int );
  50. char *SBOX0(char *);
  51. char *SBOX1(char *);
  52. void SDES::GetChar();
  53. };
  54. SDES::SDES(char *key) //Initializes the object with 10-bits key
  55. {
  56. int i;
  57. if(strlen(key)!=10) //Checks for valid length key
  58. {
  59. printf("\nInValid Key-Length %s %d",key,strlen(key));
  60. getch();
  61. exit(1);
  62. }
  63. for(i=0;i<10;i++) //Assigning the key privatly
  64. {
  65. KEY[i]=key[i];
  66. }
  67. KEY[10]='\0';
  68. GenerateKeys(); //Key Genaration Starts. Output: (K1/K2)
  69.  
  70. }
  71.  
  72. void SDES::GenerateKeys()
  73. {
  74. int P10[10]={3,5,2,7,4,10,1,9,8,6}; //P10 permutation-array
  75. char P10_OP[11]; //Output of P10 is to be stored here
  76. int P8[8]={6,3,7,4,8,5,10,9}; //P8 permutation-array
  77. char *P10LEFT,*pl,*pl1,*P10RIGHT,*pr,*pr1,*plpr;
  78. int i;
  79.  
  80. /*P10 operation is done on main key*/
  81. for(i=0;i<10;i++)
  82. P10_OP[i]=KEY[P10[i]-1];
  83.  
  84. P10_OP[10]='\0';
  85.  
  86. /*Dividing 10-bit output of P10 operation into
  87. two parts*/
  88. for(i=0;i<5;i++)
  89. {
  90. P10LEFT[i]=P10_OP[i];
  91. P10RIGHT[i]=P10_OP[i+5];
  92. }
  93. P10LEFT[5]='\0';
  94. P10RIGHT[5]='\0';
  95.  
  96. pl=new char[6];
  97. pr=new char[6];
  98.  
  99. /*Perform Left-Circular shift by 1 bit on the
  100. two parts of P10 output*/
  101. pl=Left_Shift(P10LEFT,1);
  102. pr=Left_Shift(P10RIGHT,1);
  103.  
  104. /*Combine the above two parts after
  105. the left-cicular operation into 'plpr' string*/
  106. for(i=0;i<5;i++)
  107. {
  108. plpr[i]=pl[i];
  109. plpr[i+5]=pr[i];
  110. }
  111. plpr[10]='\0';
  112.  
  113. /*Performing P8 Operation on plpr and assigning to K1*/
  114. for(i=0;i<8;i++)
  115. K1[i]=plpr[P8[i]-1];
  116.  
  117. K1[8]='\0'; //This is our first sub-key K1
  118.  
  119. /*Again performing Left-Circular-Shift(LCS) by 2 bits on
  120. the output of previous Left-Cicular-Shift(LCS)*/
  121. pl1=Left_Shift(pl,2);
  122. pr1=Left_Shift(pr,2);
  123.  
  124. /*Combining the output of above LCS2 into 1 string*/
  125. for(i=0;i<5;i++)
  126. {
  127. plpr[i]=pl1[i];
  128. plpr[i+5]=pr1[i];
  129. }
  130. plpr[10]='\0';
  131.  
  132. /*Again performing P8 operation on the above combined
  133. string*/
  134. for(i=0;i<8;i++)
  135. {
  136. K2[i]=plpr[P8[i]-1];
  137. }
  138. K2[8]='\0'; //This is our second sub-key K2
  139.  
  140. }
  141.  
  142. /*Method to perform Left-Circular-Shift on bit-string*/
  143. char *SDES::Left_Shift(char *bs,int n)
  144. {
  145. int length=strlen(bs);
  146. char *char_ptr,firstbit,*str;
  147.  
  148. char_ptr = new char[length +1];
  149. str=new char[length+1];
  150. char_ptr=bs;
  151.  
  152. int i,j;
  153. for(j=0;j<n;j++)
  154. {
  155. firstbit=char_ptr[0];
  156.  
  157. for(i=0;i<length-1;i++)
  158. {
  159. str[i]=char_ptr[i+1];
  160. }
  161. str[length-1]=firstbit;
  162. char_ptr[length]='\0';
  163. char_ptr=str;
  164. }
  165. char_ptr[length]='\0';
  166. return(str);
  167. }
  168.  
  169. /*Method to convert unsigned char to bit-string
  170. For Ex. 1="00000001"*/
  171. void SDES::conv_to_bits(unsigned char ch)
  172. {
  173. int i,bit;
  174. INPUT_BIT[8]='\0';
  175. for(i=7;i>=0;i--)
  176. {
  177. bit=ch%2;
  178. ch=ch/2;
  179.  
  180. if(bit!=0)
  181. INPUT_BIT[i]='1';
  182. else
  183. INPUT_BIT[i]='0';
  184. }
  185.  
  186. }
  187.  
  188. /*Method to perform Initial-Permutation*/
  189. void SDES::IP(char *input)
  190. {
  191. int IPArray[8]={2,6,3,1,4,8,5,7};
  192. int i;
  193. IPOutput[8]='\0';
  194. for(i=0;i<8;i++)
  195. {
  196. IPOutput[i]=input[IPArray[i]-1];
  197. }
  198. }
  199.  
  200. /*Method to perform Inverse of Initial-Permutation*/
  201. void SDES::InvIP(char *input)
  202. {
  203. int InvIPArray[8]={4,1,3,5,7,2,8,6};
  204. int i;
  205. InvIPOutput[8]='\0';
  206. for(i=0;i<8;i++)
  207. {
  208. InvIPOutput[i]=input[InvIPArray[i]-1];
  209. }
  210. }
  211.  
  212. /*Method to perform SDES-Encryption on 8-bit 'input'*/
  213. void SDES::DES_Encryption(unsigned char input)
  214. {
  215. char LIP[5],RIP[5],L1[5],R1[5];
  216. int i;
  217.  
  218. INPUT=input;
  219. conv_to_bits(INPUT); //Converts the input to bit-string
  220. IP(INPUT_BIT); //Initial-Permutation
  221.  
  222. gotoxy(1,1);
  223. printf("\nEncrpyting.........");
  224.  
  225. /*Dividing the output of IP into 2 parts*/
  226. for(i=0;i<4;i++)
  227. {
  228. LIP[i]=IPOutput[i];
  229. RIP[i]=IPOutput[i+4];
  230. }
  231. LIP[4]='\0';
  232. RIP[4]='\0';
  233.  
  234. /*Sending the above divided parts to Function_F and sub-key K1*/
  235. Function_F(LIP,RIP,1);
  236.  
  237. /*Dividing the output of the Function_F into 2 parts*/
  238. for(i=0;i<4;i++)
  239. {
  240. L1[i]=F1Output[i];
  241. R1[i]=F1Output[4+i];
  242. }
  243. L1[4]='\0';
  244. R1[4]='\0';
  245.  
  246. /*This time the string-parameters swaped and uses sub-key K2*/
  247. Function_F(R1,L1,2);
  248.  
  249. /*Performing the Inverse IP on the output of the Funtion_F*/
  250. InvIP(F1Output); //The output of the function will give us
  251. //Cipher-string
  252.  
  253. /*Cipher string is converted back to unsigned char and stored
  254. in private-variable OUTPUT of this class*/
  255. GetChar();
  256. }
  257.  
  258.  
  259. /*Decryption is just inverse of Encryption
  260. Here IP, InvIP, E/P, SBOX1 and SBOX2 are same
  261. But Function_F first operats on sub-key K2 and
  262. then on sub-key K1*/
  263. void SDES::DES_Decryption(unsigned char input)
  264. {
  265. char LIP[5],RIP[5],L1[5],R1[5];
  266. int i;
  267.  
  268. INPUT=input;
  269. conv_to_bits(INPUT);
  270. IP(INPUT_BIT); //Initial-Permutation
  271.  
  272. gotoxy(1,1);
  273. printf("\nDecrpyting.........");
  274.  
  275. for(i=0;i<4;i++)
  276. {
  277. LIP[i]=IPOutput[i];
  278. RIP[i]=IPOutput[i+4];
  279. }
  280. LIP[4]='\0';
  281. RIP[4]='\0';
  282.  
  283. Function_F(LIP,RIP,2);
  284.  
  285. for(i=0;i<4;i++)
  286. {
  287. L1[i]=F1Output[i];
  288. R1[i]=F1Output[4+i];
  289. }
  290. L1[4]='\0';
  291. R1[4]='\0';
  292.  
  293. Function_F(R1,L1,1);
  294. InvIP(F1Output);
  295. GetChar();
  296. }
  297.  
  298. void SDES::Function_F(char *linput,char *rinput,int key)
  299. {
  300. int E_P[8]={4,1,2,3,2,3,4,1}; //E/P Operation-Array
  301. int P4[4]={2,4,3,1}; //P4 Operation-Array
  302. int i;
  303. char E_POutput[9],*EXOR_Output,*LEXOR,*REXOR;
  304. char *SBOX0_Output,*SBOX1_Output;
  305. char SBOX_Output[5];
  306. char P4_Output[5];
  307. char fk_Output[5];
  308. char Main_Output[9];
  309.  
  310. /*E/P Operaion is performed here*/
  311. for(i=0;i<8;i++)
  312. {
  313. E_POutput[i]=rinput[E_P[i]-1];
  314. }
  315. E_POutput[8]='\0';
  316.  
  317. /*Bitwise-EXOR is done on E/P Output and sub-key(K1/K2)*/
  318. EXOR_Output=EX_OR(E_POutput,key);
  319.  
  320. /*Divide the output of Exor in 2 parts*/
  321. LEXOR=new char[strlen(EXOR_Output)/2+1];
  322. REXOR=new char[strlen(EXOR_Output)/2+1];
  323.  
  324. for(i=0;i<strlen(EXOR_Output)/2;i++)
  325. {
  326. LEXOR[i]=EXOR_Output[i];
  327. REXOR[i]=EXOR_Output[i+4];
  328. }
  329. LEXOR[4]=REXOR[4]='\0';
  330.  
  331.  
  332. /*Peforming SBOX0 Operation on left 4 bits*/
  333. SBOX0_Output=SBOX0(LEXOR);
  334.  
  335. /*Peforming SBOX1 Operation on right 4 bits*/
  336. SBOX1_Output=SBOX1(REXOR);
  337.  
  338. /*Combining the 2-bits output of both SBOXES in one string*/
  339. for(i=0;i<2;i++)
  340. {
  341. SBOX_Output[i]=SBOX0_Output[i];
  342. SBOX_Output[i+2]=SBOX1_Output[i];
  343. }
  344. SBOX_Output[4]='\0';
  345.  
  346. /*Performing the P4 operation on SBOX output*/
  347. for(i=0;i<4;i++)
  348. {
  349. P4_Output[i]=SBOX_Output[P4[i]-1];
  350. }
  351. P4_Output[4]='\0';
  352.  
  353. /*Performing the EXOR operation on 4-bits P4-output
  354. and 4-bits Leftinput of Funtion_F*/
  355. for(i=0;i<4;i++)
  356. {
  357. if(P4_Output[i]==linput[i])
  358. fk_Output[i]='0';
  359. else
  360. fk_Output[i]='1';
  361. }
  362. fk_Output[4]='\0';
  363.  
  364. /*Cancating the 4-bits output of above EXOR-operation
  365. and 4-bits Right-input of Function_F*/
  366. for(i=0;i<4;i++)
  367. {
  368. Main_Output[i]=fk_Output[i];
  369. Main_Output[i+4]=rinput[i];
  370. }
  371. Main_Output[8]='\0';
  372. /*Assigning this Cucaneted string to Private variable 'F1Output'*/
  373. strcpy(F1Output,Main_Output);
  374. }
  375.  
  376. /*This method EXORS the output ofE/P and sub-keys
  377. depending on the parameter k.
  378. k=1:subkey K1 k=2:subkey K2*/
  379. char *SDES::EX_OR(char *ep,int k)
  380. {
  381. char *output,*key;
  382. int i,klen;
  383.  
  384. output=new char[strlen(ep)+1];
  385. key=new char[strlen(K1)+1];
  386. if(k==1)
  387. {
  388. strcpy(key,K1);
  389. }
  390. else
  391. {
  392. if(k==2)
  393. {
  394. strcpy(key,K2);
  395. }
  396. else
  397. {
  398. printf("\n\nWrong Choice in the key parameter(1/2)");
  399. getch();
  400. exit(1);
  401. }
  402. }
  403. klen=strlen(K1);
  404. if(strlen(ep)!=klen)
  405. {
  406. printf("\ninput=%d is not equal to K=%d",strlen(ep),klen);
  407. printf("\n\nError in the Output of E/P (Length)..Press any key");
  408. getch();
  409. exit(1);
  410. }
  411. for(i=0;i<strlen(ep);i++)
  412. {
  413. if(ep[i]==key[i])
  414. output[i]='0';
  415. else
  416. output[i]='1';
  417. }
  418. output[strlen(ep)]='\0';
  419. return(output);
  420. }
  421.  
  422. /*SBOX0 Operation is defined here*/
  423. char *SDES::SBOX0(char *l)
  424. {
  425. int S0[4][4]={1,0,3,2, //S0 Matrix
  426. 3,2,1,0,
  427. 0,2,1,3,
  428. 3,1,3,2
  429. };
  430.  
  431. char *bits[]={"00","01","10","11"};
  432. char lrow[3],lcol[3];
  433. char *SO;
  434. int i,lr,lc,b;
  435.  
  436. SO=new char[3];
  437.  
  438. lrow[0]=l[0];
  439. lrow[1]=l[3];
  440. lcol[0]=l[1];
  441. lcol[1]=l[2];
  442.  
  443. lrow[2]='\0';
  444. lcol[2]='\0';
  445.  
  446.  
  447. for(i=0;i<4;i++)
  448. {
  449. if(strcmp(lrow,bits[i])==0)
  450. lr=i;
  451. if(strcmp(lcol,bits[i])==0)
  452. lc=i;
  453. }
  454. b=S0[lr][lc];
  455. for(i=0;i<3;i++)
  456. SO[i]=bits[b][i];
  457. SO[3]='\0';
  458. return(SO);
  459. }
  460. /*SBOX1 Operation is defined here*/
  461. char *SDES::SBOX1(char *l)
  462. {
  463. int S0[4][4]={0,1,2,3, //S1 Matrix
  464. 2,0,1,3,
  465. 3,0,1,0,
  466. 2,1,0,3
  467. };
  468.  
  469. char *bits[]={"00","01","10","11"};
  470. char lrow[3],lcol[3];
  471. char *SO;
  472. int i,lr,lc,b;
  473.  
  474. SO=new char[3];
  475.  
  476. lrow[0]=l[0];
  477. lrow[1]=l[3];
  478. lcol[0]=l[1];
  479. lcol[1]=l[2];
  480.  
  481. lrow[2]='\0';
  482. lcol[2]='\0';
  483.  
  484.  
  485. for(i=0;i<4;i++)
  486. {
  487. if(strcmp(lrow,bits[i])==0)
  488. lr=i;
  489. if(strcmp(lcol,bits[i])==0)
  490. lc=i;
  491. }
  492. b=S0[lr][lc];
  493. for(i=0;i<3;i++)
  494. SO[i]=bits[b][i];
  495.  
  496. SO[3]='\0';
  497. return(SO);
  498. }
  499.  
  500. /*Method to get back unsigned char from bit-string*/
  501. void SDES::GetChar()
  502. {
  503. int i,j,in;
  504. unsigned char ch=0;
  505. char *bs;
  506. bs=new char[9];
  507. bs=InvIPOutput;
  508. if(strlen(bs)>8)
  509. {
  510. printf("\nWRONG LENGTH STRING");
  511. exit(0);
  512. }
  513. for(i=0;i<8;i++)
  514. {
  515. if(bs[i]=='1')
  516. {
  517. in=1;
  518. for(j=1;j<8-i;j++)
  519. {
  520. in=in*2;
  521. }
  522. ch=ch+in;
  523. }
  524. }
  525. OUTPUT=ch;
  526. }
  527.  
  528. /*Destructor*/
  529. SDES::~SDES()
  530. {
  531. }
  532.  
  533.  
  534. void main(void)
  535. {
  536. clrscr();
  537. unsigned char ch,ch1;
  538. int i,n=10,choice;
  539. char *key;//="1010000010";
  540. char *sfname,*tfname;
  541. while(1)
  542. {
  543. key = new char[11];
  544. sfname = new char[20];
  545. tfname = new char[20];
  546. mainmenu(&choice);
  547. fflush(stdin);
  548. switch(choice)
  549. {
  550. case 1:
  551. menuEn(tfname,sfname,key);
  552. DoEnDe(tfname,sfname,key,choice);
  553. break;
  554. case 2:
  555. menuDe(tfname,sfname,key);
  556. DoEnDe(tfname,sfname,key,choice);
  557. break;
  558. case 3:
  559. exit(0);
  560. default:
  561. printf("\nWrong Choice Enter again\nPress any key to return to Main Menu..");
  562. getch();
  563. break;
  564. }
  565. }
  566. }
  567.  
  568. void mainmenu(int *c)
  569. {
  570. clrscr();
  571. printf("\nWhat do you want to do..");
  572. printf("\n1. Encryption");
  573. printf("\n2. Decryption");
  574. printf("\n3. Exit");
  575. printf("\n\nEnter the choice? ");
  576. scanf("%d",c);
  577. }
  578. void menuEn(char *t,char *s,char *k)
  579. {
  580. clrscr();
  581. printf("\nEncryption Menu\n\n");
  582. printf("\nEnter the filename to be Encrypted: ");
  583. gets(s);
  584. printf("\nEnter the Target file name: ");
  585. gets(t);
  586. printf("\nEnter the 10-bits KEY: ");
  587. gets(k);
  588. printf("\n\nNotedown this key, as same key is used for Decryption");
  589. //getch();
  590. }
  591. void menuDe(char *t,char *s,char *k)
  592. {
  593. clrscr();
  594. printf("\nDecryption Menu\n\n");
  595. printf("\nEnter the filename to be Decrypted: ");
  596. gets(s);
  597. printf("\nEnter the Target file name: ");
  598. gets(t);
  599. printf("\nEnter the 10-bits KEY: ");
  600. gets(k);
  601. }
  602.  
  603. int DoEnDe(char *t,char *s,char *k,int c)
  604. {
  605.  
  606. printf("\n\nTarget = %s Source = %s key = %s choice = %d",t,s,k,c);
  607.  
  608. SDES S(k);
  609. int i,n;
  610. n=10; //Number of Rounds
  611. unsigned char ch;
  612. FILE *fp,*ft;
  613. fp=fopen(t,"wb");
  614. ft=fopen(s,"rb");
  615. if(fp==NULL||ft==NULL)
  616. {
  617. printf("\nFile not opened SORRY");
  618. getch();
  619. fclose(ft);
  620. fclose(fp);
  621. return(0);
  622. }
  623. while(fread(&ch,1,1,ft)==1)
  624. {
  625. S.OUTPUT=ch;
  626.  
  627. for(i=0;i<n;i++)
  628. {
  629. if(c==1)
  630. S.DES_Encryption(S.OUTPUT);
  631. if(c==2)
  632. S.DES_Decryption(S.OUTPUT);
  633. }
  634. fwrite(&S.OUTPUT,1,1,fp);
  635. }
  636. printf("\nCompleted!!!!!");
  637. getch();
  638. fclose(fp);
  639. fclose(ft);
  640. return(1);
  641. }
Compilation error #stdin compilation error #stdout 0s 0KB
stdin
Standard input is empty
compilation info
prog.cpp:19:18: fatal error: conio.h: No such file or directory
 #include<conio.h>
                  ^
compilation terminated.
stdout
Standard output is empty