Giáo trình Lập trình An toàn - Chương 5: Hàm băm và xác thực thông điệp - Lương Ánh Hoàng

–  Chuỗi dữ liệu thêm vào để tăng không gian khóa và chống lại hình thức replay-¬‐attack. –  Hai bên có thể thỏa thuận chung một salt nào đó thay đổi theo thời gian. –  Salt thường được thêm vào đầu thông điệp gốc, sau đó thực hiện băm cả salt cả thông điệp.

pdf20 trang | Chia sẻ: huongthu9 | Lượt xem: 385 | Lượt tải: 0download
Bạn đang xem nội dung tài liệu Giáo trình Lập trình An toàn - Chương 5: Hàm băm và xác thực thông điệp - Lương Ánh Hoàng, để tải tài liệu về máy bạn click vào nút DOWNLOAD ở trên
Lương  Ánh  Hoàng   hoangla@soict.hut.edu.vn   Chương  5.  Hàm  băm  và  xác  thực   thông  điệp   Hashes  and  Message  Authentication   5.1  Các  loại  hàm  băm  và  MAC  thông  dụng  5.2  Băm  với  OpenSSL    5.3  Băm  dữ  liệu  với  CryptoAPI    5.4  Xác  thực  thông  điệp  với  HMAC  5.5  Salt   Nội  dung   82   •  Hàm  băm  (hashes)  –  Nhận  đầu  vào  là  một  xâu  và  đầu  ra  là  một  chuỗi  bit  có  chiều  dài  xác  định.  –  Tỉ  lệ  đụng  độ  rất  nhỏ.    –  Dùng  để  kiểm  tra  tính  toàn  vẹn  của  dữ  liệu  nhưng  không  đảm  bảo  tính  xác  thực  của  dữ  liệu.  –  Thường  kết  hợp  với  mô  hình  mã  hóa  công  khai  chứ  không  sử  dụng  một  mình.  –  Các  giải  thuật  băm  thông  dụng:  MD5,  SHA1   5.1  Các  hàm  băm  và  MAC  thông  dụng   83   •  Hàm  băm  (hashes)  5.1  Các  hàm  băm  và  MAC  thông  dụng   84   Algorithm   Digest  size   Security  conqidence   Small  message   speed  (64  bytes),  in   cycles  per  byte[2]   Large  message   speed  (8K),  in   cycles  per  byte   Uses  block  cipher   Davies-­‐Meyer-­‐ AES-­‐128   128  bits  (same  length  as  cipher  block  size)   Good   46.7  cpb   57.8  cpb   Yes   MD2   128  bits   Good  to  low   392  cpb   184  cpb   No   MD4   128  bits   Insecure   32  cpb   5.8  cpb   No   MD5   128  bits   Very  low,  may  be  insecure   40.9  cpb   7.7  cpb   No   MDC-­‐2-­‐AES-­‐128   256  bits   Very  high   93  cpb   116  cpb   Yes   MDC-­‐2-­‐DES   128  bits   Good   444  cpb   444  cpb   Yes   RIPEMD-­‐160   160  bits   High   62.2  cpb   20.6  cpb   No   SHA1   160  bits   High   53  cpb   15.9  cpb   No   SHA-­‐256   256  bits   Very  high   119  cpb   116  cpb   No   SHA-­‐384   384  bits   Very  high   171  cpb   166  cpb   No   SHA-­‐512   512  bits   Very  high   171  cpb   166  cpb   No   •  Xác  thực  thông  điệp  (Message  Authentication  Code)  –  Nhận  đầu  vào  là  một  xâu  và  một  khóa  bí  mật,  đầu  ra  là  một  mã  có  chiều  dài  xác  định.  –  Dùng  để  kiểm  tra  tính  toàn  vẹn  và  xác  thực  của  dữ  liệu.  –  Các  giải  thuật  thông  dụng:  OMAC,  CMAC,  HMAC   5.1  Các  hàm  băm  và  MAC  thông  dụng   85   •  Xác  thực  thông  điệp  (Message  Authentication  Code)  5.1  Các  hàm  băm  và  MAC  thông  dụng   86   MAC   Built  upon   Small  message   speed  (64   bytes)[4]   Large  message   speed  (8K)   Appropriate   for  hardware   Patent  restric-­‐ tions   Parallel-­‐izable   CMAC   A  universal  hash  and  AES   ~18  cpb   ~18  cpb   Yes   No   Yes   HMAC-­‐SHA1   Message  digest  function   90  cpb   20  cpb   Yes   No   No   MAC127   hash127  +  AES   ~6  cpb   ~6  cpb   Yes   No   Yes   OMAC1   AES   29.5  cpb   37  cpb   Yes   No   No   OMAC2   AES   29.5  cpb   37  cpb   Yes   No   No   PMAC-­‐AES   Block  cipher   72  cpb   70  cpb   Yes   Yes   Yes   RMAC   Block  cipher   89  cpb   80  cpb   Yes   No   No   UMAC32   UHASH  and  AES   19  cpb   cpb   No   No   Yes   XMACC-­‐SHA1   Any  cipher  or  MD  function   162  cpb   29  cpb   Yes   Yes   Yes   •  OpenSSL  cung  cấp  hai  loại  giao  diện  với  các  hàm  băm  –  Giao  diện  riêng  rẽ  với  mỗi  giải  thuật  băm  cụ  thể.  •  Mỗi  giải  thuật  băm  có  tệp  tiêu  đề  riêng  •  Tên  gọi  các  hàm  là  khác  nhau  cho  các  giải  thuật  băm.  –  Giao  diện  chung  EVP  cho  mọi  loại  hàm  băm.  •  Tệp  tiêu  đề  chung:    •  Trình  tự  sử  dụng  như  nhau:  –  Khởi  tạo  ngữ  cảnh:  EVP_DigestInit  –  Cập  nhật  dữ  liệu  băm:  EVP_DigestUpdate  –  Lấy  kết  quả:  EVP_DigestFinal.   5.2  Băm  dữ  liệu  với  OpenSSL   87   •  VD:  Băm  với  SHA1  5.2  Băm  dữ  liệu  với  OpenSSL   88    #include      int                      i;    SHA_CTX              ctx;          unsigned  char  result[SHA_DIGEST_LENGTH];    /*  SHA1  has  a  20-­‐byte  digest.  */      unsigned  char  *s1  =  (unsigned  char*)"Testing";          unsigned  char  *s2  =  (unsigned  char*)"...1...2...3...";              SHA1_Init(&ctx);          SHA1_Update(&ctx,  s1,  strlen((char*)s1));      SHA1_Update(&ctx,  s2,  strlen((char*)s2));      /*  Yes,  the  context  object  is  last.  */      SHA1_Final(result,  &ctx);      printf("SHA1(\"%s%s\")  =  ",  s1,  s2);          for  (i  =  0;    i  <  SHA_DIGEST_LENGTH;    i++)  printf("%02x",  result[i]);      printf("\n");   •  VD:  Băm  với  giao  diện  EVP  5.2  Băm  dữ  liệu  với  OpenSSL   89   #include    #include    #include        int                      i  ,  ol;      EVP_MD_CTX        ctx;      unsigned  char  *result;      unsigned  char  *s1  =  (unsigned  char*)"Testing";      unsigned  char  *s2  =  (unsigned  char*)"...1...2...3...";      EVP_DigestInit(&ctx,  EVP_sha1());      EVP_DigestUpdate(&ctx,  s1,  strlen((char*)s1));      EVP_DigestUpdate(&ctx,  s2,  strlen((char*)s2));      if  (!(result  =  (unsigned  char  *)malloc(EVP_MD_CTX_block_size(&ctx))))abort();      EVP_DigestFinal(&ctx,  result,  &ol);      printf("SHA1(\"%s%s\")  =  ",  s1,  s2);      for  (i  =  0;    i  <  ol;    i++)  printf("%02x",  result[i]);      printf("\n");        free(result);   •  Trình  tự  băm  với  CryptoAPI  –  Tệp  tiêu  đề:  Wincrypt.h  –  Khởi  tạo  ngữ  cảnh  Provider:  CryptAcquireContext  –  Tạo  đối  tượng  hash:  CryptCreateHash  –  Băm  liên  tiếp  với:  CryptHashData  –  Lấy  kết  quả:  CryptGetHashParam  –  Giải  phóng  đói  tượng  hash:  CryptDestroyHash   5.3  Băm  dữ  liệu  với  CryptoAPI   90   •  Ví  dụ:  Băm  dữ  liệu  với  thuật  toán  SHA-­‐256  5.3  Băm  dữ  liệu  với  CryptoAPI   91      BYTE                    *pbData;      DWORD                  cbData  =  sizeof(DWORD),  cbHashSize,  i;      HCRYPTHASH        hSHA256;      HCRYPTPROV        hProvider;      unsigned  char  *s1  =  (unsigned  char*)"Testing";      unsigned  char  *s2  =  (unsigned  char*)"...1...2...3...";      //  Khởi  tạo  ngữ  cảnh  Provider      CryptAcquireContext(&hProvider,  0,  MS_ENH_RSA_AES_PROV,  PROV_RSA_AES,  0);      //  Tạo  đối  tượng  hàm  băm      CryptCreateHash(hProvider,  CALG_SHA_256,  0,  0,  &hSHA256);      //  Thực  hiện  băm      CryptHashData(hSHA256,  s1,  strlen((char*)s1),  0);      CryptHashData(hSHA256,  s2,  strlen((char*)s2),  0);    //  Thực  hiện  băm         •  Ví  dụ:  Băm  dữ  liệu  với  thuật  toán  SHA-­‐256  (tiếp)  5.3  Băm  dữ  liệu  với  CryptoAPI   92      //  Lấy  kích  thước  dữ  liệu  băm  được      CryptGetHashParam(hSHA256,  HP_HASHSIZE,  (BYTE  *)&cbHashSize,  &cbData,  0);      pbData  =  (BYTE  *)LocalAlloc(LMEM_FIXED,  cbHashSize);      //  Lấy  dữ  liệu  băm  được      CryptGetHashParam(hSHA256,  HP_HASHVAL,  pbData,  &cbHashSize,  0);      //  Giải  phóng  đối  tượng  băm  và  ngữ  cảnh  Provider      CryptDestroyHash(hSHA256);      CryptReleaseContext(hProvider,  0);              printf("SHA256(\"%s%s\")  =  ",  s1,  s2);      for  (i  =  0;    i  <  cbHashSize;    i++)  printf("%02x",  pbData[i]);      printf("\n");              LocalFree(pbData);             •  Với  OpenSSL  –  Tệp  tiêu  đều    –  Gọi  hàm  HMAC_Init  để  khởi  tạo  ngữ  cảnh  và  key  sẽ  sử  dụng  –  Liên  tục  gọi  hàm  HMAC_Update  để  cập  nhật  dữ  liệu.  –  Gọi  hàm  HMAC_Final  để  kết  thúc  quá  trình  băm  –  Gọi  hàm  HMAC_cleanup  để  xóa  key  khỏi  bộ  nhớ.  –  Có  thể  gọi  hàm  All-­‐in-­‐one  HMAC  –  Bên  nhận  kiểm  tra  lại  bằng  cách  thực  hiện  băm  với  với  cùng  một  key  và  giải  thuật  và  so  sánh  kết  quả   5.4  Xác  thực  thông  điệp  với  HMAC   93   •  Với  OpenSSL  5.4  Xác  thực  thông  điệp  với  HMAC   94      int                      i;      HMAC_CTX            ctx;      unsigned  int    len;      unsigned  char  out[20];      unsigned  char  *  key  =  (unsigned  char*)"secret";      int      keylen  =  strlen((char*)key);      //  Khởi  tạo  HMAC  với  key  là  secret      HMAC_Init(&ctx,  key,  keylen,  EVP_sha1(    ));      //  Thực  hiện  băm  xâu  "fr      HMAC_Update(&ctx,  (unsigned  char*)"hash  me  pls",  11);      //  Lấy  kết  quả      HMAC_Final(&ctx,  out,  &len);      for  (i  =  0;    i  <  len;    i++)  printf("%02x",  out[i]);      printf("\n");   •  Với  CryptAPI  –  Tạo  đối  tượng  Hash  với  hàm  CryptCreateHash,  trong  đó  tham  số  hKey  là  một  key  đã  được  tạo  trước.  –  Thiết  lập  thông  tin  về  giải  thuật  băm  với  hàm  CryptSetHashParam.  –  Thực  hiện  băm  với  hàm  CryptHashData  –  Lấy  kích  thước,  nội  của  dữ  liệu  băm  được  với  hàm  CryptGetHashParam.  –  Giải  phóng  đói  tượng  Hash  và  Key     5.4  Xác  thực  thông  điệp  với  HMAC   95   •  Với  CryptAPI     5.4  Xác  thực  thông  điệp  với  HMAC   96      BYTE              out[20];      DWORD            cbData  =  sizeof(out),  i;      HCRYPTKEY    hKey;      HMAC_INFO    HMACInfo;      HCRYPTHASH  hHash;      HCRYPTPROV  hProvider;      //  Lấy  ngữ  cảnh  provider    CryptAcquireContext(&hProvider,0,MS_ENH_RSA_AES_PROV,PROV_RSA_AES,CRYPT_VERIFYCONTEXT);      //  Sinh  key  từ  mật  khẩu                  hKey  =  CreateKeyFromPassword(hProvider,"secret");      //  Tạo  đối  tượng  băm      CryptCreateHash(hProvider,  CALG_HMAC,  hKey,  0,  &hHash);         •  Với  CryptAPI     5.4  Xác  thực  thông  điệp  với  HMAC   97   //  Thiết  lập  giải  thuật  băm      HMACInfo.HashAlgid          =  CALG_SHA1;      HMACInfo.pbInnerString  =  HMACInfo.pbOuterString  =  0;      HMACInfo.cbInnerString  =  HMACInfo.cbOuterString  =  0;      CryptSetHashParam(hHash,  HP_HMAC_INFO,  (BYTE  *)&HMACInfo,  0);      //  Thực  hiện  băm        CryptHashData(hHash,  (BYTE  *)"Hash  me  plz",  11,  0);      //  Lấy  kết  quả      CryptGetHashParam(hHash,  HP_HASHVAL,  out,  &cbData,  0);      for  (i  =  0;    i  <  cbData;    i++)  printf("%02x",  out[i]);      printf("\n");              CryptDestroyHash(hHash);      CryptDestroyKey(hKey);      CryptReleaseContext(hProvider,  0);         •  Salt  –  Chuỗi  dữ  liệu  thêm  vào  để  tăng  không  gian  khóa  và  chống  lại  hình  thức  replay-­‐attack.  –  Hai  bên  có  thể  thỏa  thuận  chung  một  salt  nào  đó  thay  đổi  theo  thời  gian.  –  Salt  thường  được  thêm  vào  đầu  thông  điệp  gốc,  sau  đó  thực  hiện  băm  cả  salt  cả  thông  điệp.     5.5  Sử  dụng  Salt   98   1.  Viết  chương  trình  mã  hóa  và  giải  mã  tệp  tin  bằng  giải  thuật  AES-­‐256  bit.  Mật  khẩu  nhập  từ  bàn  phím.  Kiểm  tra  tính  đúng  đắn  của  kết  quả  bằng  giải  thuật  SHA-­‐256.  Sử  dụng  thư  viện  OpenSSL.  Khuôn  dạng  dữ  liệu  của  tệp  tin  sau  khi  mã  hóa  có  thể  như  sau:        2.  Viết  chương  trình  chat  client-­‐server  đơn  giản  trong  đó  kênh  truyền  được  mã  hóa  theo  giải  thuật  AES-­‐256.  Key  được  sinh  ra  từ  mật  khẩu  thỏa  thuận  trước  và  không  truyền  qua  mạng,  Vector  khởi  tạo  là  mã  BCD  được  thiết  lập  từ  ngày  và  giờ  hiện  tại  của  hệ  thống  (Hàm  API  GetSystemTime).  Ví  dụ:  Nếu  hiện  tại  là  07h  ngày  10/10/2011  thì  giá  trị  dưới  dạng  hexa  của  vector  khởi  tạo  là   2011101007000.00     Bài  tập   99   3.  Viết  chương  trình  băm  nội  dung  một  }ile  bằng  giải  thuật  HMAC-­‐AES256,  sử  dụng  thư  viện  OpenSSL.  Mật  khẩu  để  băm  nhập  từ  bàn  phím.Kết  quả  băm  được  lưu  vào  cuối  }ile.  4.  Viết  chương  trình  kiểm  tra  tính  toàn  vẹn  của  một  }ile  bằng  giải  thuật  HMAC-­‐AES256.  Mật  khẩu  để  kiểm  tra  nhập  từ  bàn  phím.     Bài  tập   100  

Các file đính kèm theo tài liệu này:

  • pdfgiao_trinh_lap_trinh_an_toan_chuong_5_ham_bam_va_xac_thuc_th.pdf
Tài liệu liên quan