Linux下DES安全通信编程

des.h

/*********************************************************************/
/*-文件名:des.h
/*-功能: 实现DES加密算法的加密解密功能    for linux
/*********************************************************************/
#define SUCCESS 1;
typedef  int INT32;
typedef  char INT8;
typedef  unsigned char  ULONG8;
typedef  unsigned short ULONG16;
typedef  unsigned long  ULONG32;
static const ULONG8 DESENCRY=11;
static const ULONG8 DESDECRY=22;
static const ULONG8  pc_first[64] = {/*初始置换IP*/
     58,50,42,34,26,18,10,2,60,52,44,36,28,20,12,4,
     62,54,46,38,30,22,14,6,64,56,48,40,32,24,16,8,
     57,49,41,33,25,17,9,1,59,51,43,35,27,19,11,3,
     61,53,45,37,29,21,13,5,63,55,47,39,31,23,15,7 } ;
static const ULONG8 pc_last[64] = { /*逆初始置换IP-1*/
  40,8,48,16,56,24,64,32, 39,7,47,15,55,23,63,31,
  38,6,46,14,54,22,62,30, 37,5,45,13,53,21,61,29,
  36,4,44,12,52,20,60,28, 35,3,43,11,51,19,59,27,
  34,2,42,10,50,18,58,26, 33,1,41,9,49,17,57,25};
static const ULONG32  pc_by_bit[64] = { /*按位取值或赋值*/
   0x80000000L,0x40000000L,0x20000000L,0x10000000L, 0x8000000L, 
   0x4000000L, 0x2000000L, 0x1000000L, 0x800000L, 0x400000L,
   0x200000L, 0x100000L,  0x80000L, 0x40000L, 0x20000L,0x10000L, 
   0x8000L, 0x4000L, 0x2000L, 0x1000L, 0x800L, 0x400L, 0x200L,
   0x100L, 0x80L,0x40L,0x20L, 0x10L, 0x8L, 0x4L, 0x2L, 0x1L,
   0x80000000L,0x40000000L,0x20000000L,0x10000000L, 0x8000000L,
   0x4000000L, 0x2000000L, 0x1000000L, 0x800000L, 0x400000L,
   0x200000L, 0x100000L,  0x80000L, 0x40000L, 0x20000L, 0x10000L, 
   0x8000L, 0x4000L, 0x2000L, 0x1000L, 0x800L, 0x400L, 0x200L, 
   0x100L, 0x80L, 0x40L,0x20L, 0x10L, 0x8L,  0x4L, 0x2L, 0x1L,   };
static const ULONG8 des_P[32] = {/*置换运算P*/
       16,7,20,21, 29,12,28,17, 1,15,23,26,
       5,18,31,10, 2,8,24,14, 32,27,3,9,
       19,13,30,6, 22,11,4,25};
static const ULONG8 des_E[48] = {/*数据扩展*/
        32,1,2,3,4,5,4,5,6,7,8,9,8,9,10,11,12,13,
        12,13,14,15,16,17,16,17,18,19,20,21,
        20,21,22,23,24,25,24,25,26,27,28,29,
        28,29,30,31,32,1 };
static const ULONG8 des_S[8][64] = {/*数据压缩*/
  {
    0xe,0x0,0x4,0xf,0xd,0x7,0x1,0x4,0x2,0xe,0xf,0x2,0xb,
    0xd,0x8,0x1,0x3,0xa,0xa,0x6,0x6,0xc,0xc,0xb,0x5,0x9,
    0x9,0x5,0x0,0x3,0x7,0x8,0x4,0xf,0x1,0xc,0xe,0x8,0x8,
    0x2,0xd,0x4,0x6,0x9,0x2,0x1,0xb,0x7,0xf,0x5,0xc,0xb,
    0x9,0x3,0x7,0xe,0x3,0xa,0xa,0x0,0x5,0x6,0x0,0xd  
  },
  { 
    0xf,0x3,0x1,0xd,0x8,0x4,0xe,0x7,0x6,0xf,0xb,0x2,0x3,
    0x8,0x4,0xf,0x9,0xc,0x7,0x0,0x2,0x1,0xd,0xa,0xc,0x6,
    0x0,0x9,0x5,0xb,0xa,0x5,0x0,0xd,0xe,0x8,0x7,0xa,0xb,
    0x1,0xa,0x3,0x4,0xf,0xd,0x4,0x1,0x2,0x5,0xb,0x8,0x6,
    0xc,0x7,0x6,0xc,0x9,0x0,0x3,0x5,0x2,0xe,0xf,0x9
  },
  { 
    0xa,0xd,0x0,0x7,0x9,0x0,0xe,0x9,0x6,0x3,0x3,0x4,0xf,
    0x6,0x5,0xa,0x1,0x2,0xd,0x8,0xc,0x5,0x7,0xe,0xb,0xc,
    0x4,0xb,0x2,0xf,0x8,0x1,0xd,0x1,0x6,0xa,0x4,0xd,0x9,
    0x0,0x8,0x6,0xf,0x9,0x3,0x8,0x0,0x7,0xb,0x4,0x1,0xf,
    0x2,0xe,0xc,0x3,0x5,0xb,0xa,0x5,0xe,0x2,0x7,0xc                                          
  },
  { 
    0x7,0xd,0xd,0x8,0xe,0xb,0x3,0x5,0x0,0x6,0x6,0xf,0x9,
    0x0,0xa,0x3,0x1,0x4,0x2,0x7,0x8,0x2,0x5,0xc,0xb,0x1,
    0xc,0xa,0x4,0xe,0xf,0x9,0xa,0x3,0x6,0xf,0x9,0x0,0x0,
    0x6,0xc,0xa,0xb,0xa,0x7,0xd,0xd,0x8,0xf,0x9,0x1,0x4,
    0x3,0x5,0xe,0xb,0x5,0xc,0x2,0x7,0x8,0x2,0x4,0xe                         
  },
  { 
    0x2,0xe,0xc,0xb,0x4,0x2,0x1,0xc,0x7,0x4,0xa,0x7,0xb,
    0xd,0x6,0x1,0x8,0x5,0x5,0x0,0x3,0xf,0xf,0xa,0xd,0x3,
    0x0,0x9,0xe,0x8,0x9,0x6,0x4,0xb,0x2,0x8,0x1,0xc,0xb,
    0x7,0xa,0x1,0xd,0xe,0x7,0x2,0x8,0xd,0xf,0x6,0x9,0xf,
    0xc,0x0,0x5,0x9,0x6,0xa,0x3,0x4,0x0,0x5,0xe,0x3
  },
  { 
    0xc,0xa,0x1,0xf,0xa,0x4,0xf,0x2,0x9,0x7,0x2,0xc,0x6,
    0x9,0x8,0x5,0x0,0x6,0xd,0x1,0x3,0xd,0x4,0xe,0xe,0x0,
    0x7,0xb,0x5,0x3,0xb,0x8,0x9,0x4,0xe,0x3,0xf,0x2,0x5,
    0xc,0x2,0x9,0x8,0x5,0xc,0xf,0x3,0xa,0x7,0xb,0x0,0xe,
    0x4,0x1,0xa,0x7,0x1,0x6,0xd,0x0,0xb,0x8,0x6,0xd
  },
  { 
    0x4,0xd,0xb,0x0,0x2,0xb,0xe,0x7,0xf,0x4,0x0,0x9,0x8,
    0x1,0xd,0xa,0x3,0xe,0xc,0x3,0x9,0x5,0x7,0xc,0x5,0x2,
    0xa,0xf,0x6,0x8,0x1,0x6,0x1,0x6,0x4,0xb,0xb,0xd,0xd,
    0x8,0xc,0x1,0x3,0x4,0x7,0xa,0xe,0x7,0xa,0x9,0xf,0x5,
    0x6,0x0,0x8,0xf,0x0,0xe,0x5,0x2,0x9,0x3,0x2,0xc
  },
  { 
    0xd,0x1,0x2,0xf,0x8,0xd,0x4,0x8,0x6,0xa,0xf,0x3,0xb,
    0x7,0x1,0x4,0xa,0xc,0x9,0x5,0x3,0x6,0xe,0xb,0x5,0x0,
    0x0,0xe,0xc,0x9,0x7,0x2,0x7,0x2,0xb,0x1,0x4,0xe,0x1,
    0x7,0x9,0x4,0xc,0xa,0xe,0x8,0x2,0xd,0x0,0xf,0x6,0xc,
    0xa,0x9,0xd,0x0,0xf,0x3,0x3,0x5,0x5,0x6,0x8,0xb
  } };
static const ULONG8 keyleft[28] = {/*等分密钥*/
  57,49,41,33,25,17,9,1,58,50,42,34,26,18,
  10,2,59,51,43,35,27,19,11,3,60,52,44,36};
  
static const ULONG8 keyright[28] = {/*等分密钥*/
  63,55,47,39,31,23,15,7,62,54,46,38,30,22,
  14,6,61,53,45,37,29,21,13,5,28,20,12,4};
static const ULONG8 lefttable[16] = {1,1,2,2,2,2,2,2,1,2,2,2,2,2,2,1};/*密钥移位*/
static const ULONG8 keychoose[48] ={/*密钥选取*/
  14,17,11,24,1,5,3,28,15,6,21,10,
  23,19,12,4,26,8,16,7,27,20,13,2,
  41,52,31,37,47,55,30,40,51,45,33,48,
  44,49,39,56,34,53,46,42,50,36,29,32};
static const ULONG32 wz_leftandtab[3] = {0x0 , 0x80000000 , 0xc0000000 } ;

class CDesOperate
{
private:
 ULONG32 m_arrOutKey[16][2];/*输出的key*/
 ULONG32 m_arrBufKey[2];/*形成起始密钥*/
 INT32 MakeData(ULONG32  *left ,ULONG32  *right ,ULONG32 number) 
 {
  INT32 j; 
  ULONG32 oldright = *right;         
  ULONG8 rexpbuf[8] = { 0} ;
  ULONG32 datatmp = 0;        
  ULONG32 exdes_P[2] = { 0} ;                         
  //由32扩充至48位
  
  for ( j = 0 ; j < 48 ; j++)
  {
   /*两个32位,每个存放24位*/
   if ( j < 24 )
   {
    if ( *right&pc_by_bit[des_E[j]-1] )
    {
     exdes_P[0] |= pc_by_bit[j] ;
    }            
   }            
   else
   {
    if ( *right&pc_by_bit[des_E[j]-1] )
    {
     exdes_P[1] |= pc_by_bit[j-24] ;
    }
   }
  }
  
  for ( j = 0 ; j < 2 ; j++)
  {            
   exdes_P[j] ^= m_arrOutKey[number][j] ;
  }    
  
  /*由48->32*/      
  
  exdes_P[1] >>= 8 ;
  rexpbuf[7] = (ULONG8) (exdes_P[1]&0x0000003fL) ;
  exdes_P[1] >>= 6 ;
  rexpbuf[6] = (ULONG8) (exdes_P[1]&0x0000003fL) ;
  exdes_P[1] >>= 6 ;
  rexpbuf[5] = (ULONG8) (exdes_P[1]&0x0000003fL) ;
  exdes_P[1] >>= 6 ;
  rexpbuf[4] = (ULONG8) (exdes_P[1]&0x0000003fL) ;
  exdes_P[0]  >>=  8 ;
  rexpbuf[3] = (ULONG8) (exdes_P[0]&0x0000003fL) ;     
  exdes_P[0] >>= 6 ;
  rexpbuf[2] = (ULONG8) (exdes_P[0]&0x0000003fL) ;
  exdes_P[0] >>= 6 ;
  rexpbuf[1] = (ULONG8) (exdes_P[0]&0x0000003fL) ;
  exdes_P[0] >>= 6 ;
  rexpbuf[0] = (ULONG8) (exdes_P[0]&0x0000003fL) ;     
  exdes_P[0] = 0 ;
  exdes_P[1] = 0 ;
  
  /*由48-> 32*/
  
  *right = 0 ;
  for ( j = 0 ; j < 7 ; j++)
  {
   *right |= des_S[j][rexpbuf[j]] ;
   *right <<= 4 ;
  }
  *right |= des_S[j][rexpbuf[j]] ;
  
  /*又要换位了*/
  
  datatmp = 0;
  for ( j = 0 ; j < 32 ; j++)
  {
   if ( *right&pc_by_bit[des_P[j]-1] )
   {
    datatmp |= pc_by_bit[j] ;
   }
  }
  *right = datatmp ;
  
  /*一轮结束收尾操作*/                
  
  *right ^= *left;       
  *left = oldright;
  
  return SUCCESS;
 }
 INT32 HandleData(ULONG32 *left , ULONG8 choice)
 {
  INT32  number = 0 ,j = 0;   
  ULONG32 *right = &left[1] ;
  ULONG32 tmp = 0;       
  ULONG32 tmpbuf[2] = { 0 };             
  
  /*第一次调整pc_first[64]*/
  for ( j = 0 ; j < 64 ; j++)
  {
   if (j < 32 ) 
   {
    if ( pc_first[j] > 32)/*属于right*/
    {
     if ( *right&pc_by_bit[pc_first[j]-1] )
     {
      tmpbuf[0] |= pc_by_bit[j] ;
     }
    }
    else
    {
     if ( *left&pc_by_bit[pc_first[j]-1] )
     {
      tmpbuf[0] |= pc_by_bit[j] ;
     }
    }
   }
   else
   {
    if ( pc_first[j] > 32)/*属于right*/
    {
     if ( *right&pc_by_bit[pc_first[j]-1] )
     {
      tmpbuf[1] |= pc_by_bit[j] ;
     }
    }
    else
    {
     if ( *left&pc_by_bit[pc_first[j]-1] )
     {
      tmpbuf[1] |= pc_by_bit[j] ;
     }
    }
   }
  }
  *left  = tmpbuf[0];
  *right = tmpbuf[1];
  tmpbuf[0] = 0 ;
  tmpbuf[1] = 0 ;
  
  switch(choice)
  {
  case DESENCRY:
   for ( number = 0 ; number < 16 ; number++)
   {            
    MakeData( left , right , (ULONG32)number);
   }
   break;
  case DESDECRY:
   for (number=15;number>=0;number--)
   {            
    MakeData( left , right ,(ULONG32)number);
   }
   break;
  default:
   break;
  }
  
  /*最后一轮操作不交换左右值*/
  
  tmp = *left ;
  *left = *right ;
  *right = tmp ;        
  
  /*最后一次调整pc_last[64]*/
  
  for ( j = 0 ; j < 64 ; j++)
  {
   if (j < 32 ) 
   {
    if ( pc_last[j] > 32)/*属于right*/
    {
     if ( *right&pc_by_bit[pc_last[j]-1] )
     {
      tmpbuf[0] |= pc_by_bit[j] ;
     }
    }
    else
    {
     if ( *left&pc_by_bit[pc_last[j]-1] )
     {
      tmpbuf[0] |= pc_by_bit[j] ;
     }
    }
   }
   else
   {
    if ( pc_last[j] > 32)/*属于right*/
    {
     if ( *right&pc_by_bit[pc_last[j]-1] )
     {
      tmpbuf[1] |= pc_by_bit[j] ;
     }
    }
    else
    {
     if ( *left&pc_by_bit[pc_last[j]-1] )
     {
      tmpbuf[1] |= pc_by_bit[j] ;
     }
    }
   }
  }
  
  *left =  tmpbuf[0] ;
  *right = tmpbuf[1];
  
  return SUCCESS;
 }
 INT32 MakeKey(  ULONG32 *keyleft,ULONG32 *keyright ,ULONG32 number)
 {
  ULONG32 tmpkey[2] ={0};
  ULONG32 *Ptmpkey = (ULONG32*)tmpkey;     
  ULONG32 *Poutkey = (ULONG32*)&m_arrOutKey[number]; 
  INT32 j;        
  memset((ULONG8*)tmpkey,0,sizeof(tmpkey));          
  /*要最高的一位或两位*/
  *Ptmpkey = *keyleft&wz_leftandtab[lefttable[number]] ;           
  Ptmpkey[1] = *keyright&wz_leftandtab[lefttable[number]] ;              
  if ( lefttable[number] == 1)
  {
   *Ptmpkey >>= 27;
   Ptmpkey[1] >>= 27;
  }
  else
  {
   *Ptmpkey >>= 26;
   Ptmpkey[1] >>= 26;                    
  }
  Ptmpkey[0] &= 0xfffffff0;
  Ptmpkey[1] &= 0xfffffff0;
  /*得到高位的值*/
  *keyleft <<= lefttable[number] ;
  *keyright <<= lefttable[number] ;
  *keyleft |= Ptmpkey[0] ;
  *keyright |= Ptmpkey[1] ;            
  Ptmpkey[0] = 0;
  Ptmpkey[1] = 0;
     
  /*从56位中选出48位,3个16位*/
  for ( j = 0 ; j < 48 ; j++)
  {
   if ( j < 24 )
   {
    
    if ( *keyleft&pc_by_bit[keychoose[j]-1])
    {
     Poutkey[0] |= pc_by_bit[j] ;
    }                   
   }            
   
   else /*j>=24*/
   {                   
    if ( *keyright&pc_by_bit[(keychoose[j]-28)])
    {
     Poutkey[1] |= pc_by_bit[j-24] ;
    }                   
   }
  }
  return SUCCESS;
 }

 INT32 MakeFirstKey( ULONG32 *keyP )
 {
  ULONG32 key[2] = {0};
  ULONG32 *Pkey ;
  ULONG32 *Pbufkey ;
  INT32 j; 
  Pbufkey = (ULONG32*)m_arrBufKey ;
  Pkey = (ULONG32*)key;
  
  memset((ULONG8*)m_arrBufKey,0,sizeof(m_arrBufKey));    
  memcpy((ULONG8*)&key,(ULONG8*)keyP ,8) ;      
  memset((ULONG8*)m_arrOutKey,0,sizeof(m_arrOutKey));
  for(  j = 0 ; j < 28 ; j++)
  {
   if ( keyleft[j] > 32 ) 
   {
    if ( Pkey[1]&pc_by_bit[keyleft[j]-1] )
    {
     Pbufkey[0] |= pc_by_bit[j] ;
    }
   }
   else
   {
    if ( Pkey[0]&pc_by_bit[keyleft[j]-1] )
    {
     Pbufkey[0] |= pc_by_bit[j] ;
    }
   }
   
   if ( keyright[j] > 32 ) 
   {
    if ( Pkey[1]&pc_by_bit[keyright[j]-1] )
    {
     Pbufkey[1] |= pc_by_bit[j];
    }
   }
   else
   {
    if ( Pkey[0]&pc_by_bit[keyright[j]-1] )
    {
     Pbufkey[1] |= pc_by_bit[j];
    }
   }
  }
  for (j = 0 ; j < 16 ; j++)
  {
   MakeKey(&Pbufkey[0],&Pbufkey[1] , j ) ;
  }
  return SUCCESS;
 }

 
public:
 CDesOperate()
 {
  for(int i =0 ;i<2;i++)
  {
   for(int j = 0;j<16;j++)
   {
    this->m_arrOutKey[j][i] = 0;
   }
   this->m_arrBufKey[i] = 0;
  }
 }
 INT32 Encry(char* pPlaintext,int nPlaintextLength,char *pCipherBuffer,int &nCipherBufferLength, char *pKey,int nKeyLength)
 {
  if(nKeyLength != 8)
  {
   return 0;
  }
  MakeFirstKey((ULONG32 *)pKey);
  int nLenthofLong = ((nPlaintextLength+7)/8)*2;
  if(nCipherBufferLength<nLenthofLong*4)
  {//out put buffer is not enough
   nCipherBufferLength=nLenthofLong*4;
   return 0;
  }
  memset(pCipherBuffer,0,nCipherBufferLength);
  ULONG32 *pOutPutSpace = (ULONG32 *)pCipherBuffer;
  ULONG32 *pSource;
  if(nPlaintextLength != sizeof(ULONG32)*nLenthofLong)
  {
   pSource = new ULONG32[nLenthofLong];
   memset(pSource,0,sizeof(ULONG32)*nLenthofLong);
   memcpy(pSource,pPlaintext,nPlaintextLength);
  }
  else
  {
   pSource = (ULONG32 *)pPlaintext;
  }
  ULONG32 gp_msg[2] = {0,0};
  for (int i=0;i<(nLenthofLong/2);i++)
  {
   gp_msg[0] = pSource[2*i];
   gp_msg[1] =pSource[2*i+1];
   HandleData(gp_msg,DESENCRY);
   pOutPutSpace[2*i] = gp_msg[0];
   pOutPutSpace[2*i+1] = gp_msg[1];
  }
  if(pPlaintext!=(char *)pSource)
  {
   delete []pSource;
  }
     
  return SUCCESS;
 }
 INT32 Decry(char* pCipher,int nCipherBufferLength,char *pPlaintextBuffer, int &nPlaintextBufferLength, char *pKey,int nKeyLength)
 {
  if(nCipherBufferLength%8!=0)
  {
   return 0;
  }
  if(nPlaintextBufferLength<nCipherBufferLength)
  {
   nPlaintextBufferLength = nCipherBufferLength;
   return 0;
  }
  if(nKeyLength != 8)
  {
   return 0;
  }
  MakeFirstKey((ULONG32 *)pKey);
  memset(pPlaintextBuffer,0,nPlaintextBufferLength);
  ULONG32 *pSouce = (ULONG32 *)pCipher;
  ULONG32 *pDest = (ULONG32 *)pPlaintextBuffer;
  ULONG32 gp_msg[2] = {0,0};
  for (int i=0;i<(nCipherBufferLength/8);i++)
  {
   gp_msg[0] = pSouce[2*i];
   gp_msg[1] = pSouce[2*i+1];
   HandleData(gp_msg,DESDECRY);
   pDest[2*i] = gp_msg[0];
   pDest[2*i+1] = gp_msg[1];
  }
  return SUCCESS;
 }
};

chat.cpp

#include <stdio.h>
#include <netdb.h>
#include <unistd.h>
#include <iostream>
#include <stdlib.h>
#include <errno.h>
#include <net/if.h>
#include <string.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/wait.h>
#include <arpa/inet.h> 
#include <memory.h>
#include <sys/ioctl.h>
#include "des.h"
using namespace std;
#define SERVERPORT 9527
#define BUFFERSIZE 32 
char strStdinBuffer[BUFFERSIZE];
char strSocketBuffer[BUFFERSIZE];
char strEncryBuffer[BUFFERSIZE];
char strDecryBuffer[BUFFERSIZE];
void SecretChat(int nSock,char *pRemoteName, char *pKey)
{
 CDesOperate cDes;
 if(strlen(pKey)!=8)
 {
  printf("Key length error");
  return ;
 }
 
 pid_t nPid;
 nPid = fork();
 if(nPid != 0)
 {
  while(1)
  {
   bzero(&strSocketBuffer, BUFFERSIZE);
   int nLength = 0;
   nLength = recv(nSock, strSocketBuffer,BUFFERSIZE,0);
   if(nLength !=BUFFERSIZE)
   {
    break;
   }
   else
   {
    int nLen = BUFFERSIZE;
    cDes.Decry(strSocketBuffer,BUFFERSIZE,strDecryBuffer,nLen,pKey,8);
    strDecryBuffer[BUFFERSIZE-1]=0;
    if(strDecryBuffer[0]!=0&&strDecryBuffer[0]!=‘\n‘)
    {
     printf("Receive message form <%s>: %s\n", pRemoteName,strDecryBuffer);
     if(0==memcmp("quit",strDecryBuffer,4))
     {
      printf("Quit!\n");
      break;
     }
    }
   }
  }
 }
 else
 { 
  while(1)
  {
   bzero(&strStdinBuffer, BUFFERSIZE);
   while(strStdinBuffer[0]==0)
   {
    if (fgets(strStdinBuffer, BUFFERSIZE, stdin) == NULL) 
    {
     continue;
    }
   }      
   int nLen = BUFFERSIZE;
   cDes.Encry(strStdinBuffer,BUFFERSIZE,strEncryBuffer,nLen,pKey,8);
   if(send(nSock, strEncryBuffer, BUFFERSIZE,0)!=BUFFERSIZE)
   {
    perror("send");
   }
   else
   {
    if(0==memcmp("quit",strStdinBuffer,4))
    {
     printf("Quit!\n");
     break;
    }
   }
  }
 }  
}
int main(int argc,char * [])
{
 printf("Client or Server?\r\n");
 cin>>strStdinBuffer;
 if(strStdinBuffer[0]==‘c‘||strStdinBuffer[0]==‘C‘)
 {//be a client
  char strIpAddr[16];
  printf("Please input the server address:\r\n");
  cin>>strIpAddr;
  int nConnectSocket, nLength;
  struct sockaddr_in sDestAddr;
  if ((nConnectSocket = socket(AF_INET, SOCK_STREAM, 0)) < 0) 
  {
   perror("Socket");
   exit(errno);
  }
  bzero(&sDestAddr, sizeof(sDestAddr));
  sDestAddr.sin_family = AF_INET;
  sDestAddr.sin_port = htons(SERVERPORT);
  sDestAddr.sin_addr.s_addr = inet_addr(strIpAddr);
          /* 连接服务器 */
  if (connect(nConnectSocket, (struct sockaddr *) &sDestAddr, sizeof(sDestAddr)) != 0) 
  {
   perror("Connect ");
   exit(errno);
  }
  else
  {
   printf("Connect Success!  \nBegin to chat...\n");
   SecretChat(nConnectSocket,strIpAddr,"benbenmi");
  }
        close(nConnectSocket);  
 }
 else
 {//be a server
  int nListenSocket, nAcceptSocket;
  socklen_t nLength = 0;
  struct sockaddr_in sLocalAddr, sRemoteAddr;
  if ((nListenSocket = socket(PF_INET, SOCK_STREAM, 0)) == -1) 
  {
   perror("socket");
   exit(1);
  }
  
  bzero(&sLocalAddr, sizeof(sLocalAddr));
  sLocalAddr.sin_family = PF_INET;
  sLocalAddr.sin_port = htons(SERVERPORT);
  sLocalAddr.sin_addr.s_addr = INADDR_ANY;
  
  if (bind(nListenSocket, (struct sockaddr *) &sLocalAddr, sizeof(struct sockaddr))== -1)
  {
   perror("bind");
   exit(1);
  }
  if (listen(nListenSocket, 5) == -1) 
  {
   perror("listen");
   exit(1);
  }
  printf("Listening...\n");
  nLength = sizeof(struct sockaddr);
  if ((nAcceptSocket = accept(nListenSocket, (struct sockaddr *) &sRemoteAddr,&nLength)) == -1) 
  {
   perror("accept");
   exit(errno);
  } 
  else
  {
   close(nListenSocket);
   printf("server: got connection from %s, port %d, socket %d\n",inet_ntoa(sRemoteAddr.sin_addr),ntohs(sRemoteAddr.sin_port), nAcceptSocket);
   SecretChat(nAcceptSocket,inet_ntoa(sRemoteAddr.sin_addr),"benbenmi");
   close(nAcceptSocket);
   
  }
 }
}
时间: 2024-10-11 13:03:56

Linux下DES安全通信编程的相关文章

Linux下C++的编程——开偏介绍

C++是一个功能强大而又应用广泛的计算机语言,就应用领域而言,几乎无所不在,因为有操作系统的地方就会有C++的存在,热门程序而言,也就仅次于C和Java.而C与C++又有天然的血缘关系. 从事C++开发近两年,虽然开发的产品都是跨平台的,但个人直接接触到的编程工程还是更偏重于Windows平台(至少开发环境更多的是在Windows平台,还写过"带你玩转Visual Studio"系列的博文),而现在要自己独立地带领一个项目的开发,还是一个跨平台的项目,也就有必要到Linux下C++的编

Linux下C++的编程——开发环境搭建与第一个程序

上一篇文章Linux下C++的编程--开偏介绍中我们已经介绍了GUN.GCC.G++等一些重要的概念,现在应该开始动手实践了! 开发工具的安装 环境 Distributions版本:CentOS 6.7 Linux内核片:2.6.32-573.3.1.el6.i686 一般Linux安装完之后默认就已经安装了GCC(GNU Compiler Collection),你可以查看一下gcc和g++的版本号检查gcc和g++是否已经安装. [luowf@luoweifu ~]$ gcc -v gcc

LINUX下C语言编程基础

实验二 Linux下C语言编程基础 一.实验目的 1. 熟悉Linux系统下的开发环境 2. 熟悉vi的基本操作 3. 熟悉gcc编译器的基本原理 4. 熟练使用gcc编译器的常用选项 5 .熟练使用gdb调试技术 6. 熟悉makefile基本原理及语法规范 7. 掌握静态库和动态库的生成 二.实验步骤 1. 快捷键 Ubuntu中: 2. vim VIM是一个非常好的文本编辑器,很多专业程序员使用VIM编辑代码,即使以后你不编写程序,只要跟文本打交道,都应该学学VIM,可以浏览参考一下普通人

Linux下C++的编程——GDB进行程序调试

GDB简介 我们在Linux下C++的编程--开偏介绍一文中已经简单介绍了GDB的功能,是类Unix系统的主要调试工具,可进行断点调试,跟踪程序,动态改变执行环境等功能. 从一个程序开始调试 下面我们就从一个程序开始讲解一下GDB的简单用法.假设我们有如下的程序: GDBTest1.cpp #include <iostream> int Accumulation(int n) { int result = 0; for(int i = 0; i < n; i ++) { result +

Linux下的shell编程入门

通常情况下,我们从命令行输入命令每输入一次就能够得到系统的一次响应.一旦需要我们一个接着一个的输入命令而最后才得到结果的时候,这样的做法显然就没有效率.要达到这样的目的,通常我们利用shell程序或者shell脚本来实现. 一.简介 Shell编程有很多类似C语言和其他程序语言的特征,但是又没有编程语言那样复杂.Shell程序就是放在一个文件中的一系列Linux命令和实用程序,在执行的时候,通过Linux一个接着一个地解释和执行每个命令. 下面我们来看一个简单的shell程序: 1.首先建立一个

linux下的bash编程简要学习

linux下的bash编程简要学习     1.bash是什么: linux运行时系统只会运行系统运行所需要的运行脚本即系统守护进程,一般根据用户自己需求设定和实现的服务需要手动启动,这种服务进程通常由bash启动,脚本中的命令通常被按照一定规则被bash读取视作参数,因此在脚本头部要申明运行的bash类型,bash命令分为内建命令及外部命令,外部命令通过PATH进行依次查找. bash读取命令后将其启动(fork)成为一个进程,依次启动服务     2.bash控制语句:         本地

Linux 下IO端口编程访问

以前写的一篇笔记,偶尔翻出来了,放在这里做个纪念 Linux 下IO端口编程访问 这里记录的方法是在用户态访问IO端口,不涉及驱动程序的编写. 首先要包含头文件 /usr/include/asm/io.h ioperm() 在 unistd.h 中声明.用来打开对IO端口的访问权限,要求程序执行时必须有root 权限.只可以打开0x00到0x3ff 这一地址段的IO端口. ioperm( from, num, turn_on) 比如: #include<asm/io.h> #include&l

Linux下C语言编程基础学习记录

VIM的基本使用  LINUX下C语言编程 用gcc命令编译运行C语言文件 预处理阶段:将*.c文件转化为*.i预处理过的C程序. 编译阶段:将*.i文件编译为汇编代码*.s文件. 汇编阶段:将*.s文件转化为*.o的二进制目标代码文件. 链接阶段:将*.o文件转化为可执行文件. 生成可执行文件:将*.o转换为可执行文件. 执行可执行C语言文件. gcc常用选项列表 -c      只编译不链接,生成目标文件“.o” -S      只编译不汇编,生成编码代码 -E      只进行预编译,不做

Linux下TCP网络编程与基于Windows下C#socket编程间通信

一.linux下TCP网络编程基础,需要了解相关函数 Socket():用于套接字初始化. Bind():将 socket 与本机上的一个端口绑定,就可以在该端口监听服务请求. Listen():使socket处于被动的监听模式,并为该  socket  建立一个输入数据队列,将到达的服务器, 请求保存在此队列中,直到程序处理他们. Accept():让服务器接收客户的连接请求. Connect():客户端使用connect函数来配置 socket并与远端服务器建立一个 TCP 连接. Clos