C++ Library to handle BagIt structures. BagIt is a standard format to create transfer packages for digital preservation purposes. See https://en.wikipedia.org/wiki/BagIt for details http://andreas-romeyke.de
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

106 lines
3.2 KiB

  1. #include <iostream>
  2. #include <iomanip>
  3. #include <fstream>
  4. #include <sstream>
  5. #include "checksum.hpp"
  6. #include <string>
  7. string string_of_algorithm( checksum_algorithms alg) {
  8. switch( alg ) {
  9. case md5: return string("md5");
  10. case sha1: return string("sha1");
  11. case sha256: return string("sha256");
  12. }
  13. return string("");
  14. }
  15. string Checksum::checksum_of_file(const string& filepath, checksum_algorithms alg) {
  16. ifstream file (filepath, ios::ate);
  17. stringstream hex_result;
  18. // log << "processing file '" << filepath << "'" << endl;
  19. if (file.is_open() ) {
  20. ifstream::pos_type fileSize;
  21. unsigned char * memBlock;
  22. fileSize = file.tellg();
  23. memBlock = new unsigned char[fileSize];
  24. if (nullptr != memBlock) {
  25. file.seekg(0,ios::beg);
  26. file.read(reinterpret_cast<char*>(memBlock), fileSize);
  27. switch ( alg ) {
  28. case md5: {
  29. unsigned char result[MD5_DIGEST_LENGTH];
  30. MD5(memBlock, fileSize, result);
  31. for (unsigned char i : result) {
  32. hex_result<< hex << setw(2) << setfill('0') << static_cast<int>( i);
  33. }
  34. break;
  35. }
  36. case sha1: {
  37. unsigned char result[SHA_DIGEST_LENGTH];
  38. SHA1(memBlock, fileSize, result);
  39. for (unsigned char i : result) {
  40. hex_result<< hex << setw(2) << setfill('0') << static_cast<int>( i);
  41. }
  42. break;
  43. }
  44. case sha256: {
  45. unsigned char result[SHA_DIGEST_LENGTH];
  46. SHA256( memBlock, fileSize, result);
  47. for (unsigned char i : result) {
  48. hex_result<< hex << setw(2) << setfill('0') << static_cast<int>( i);
  49. }
  50. break;
  51. }
  52. }
  53. delete[] memBlock;
  54. // log << "# # CHECKSUM for filepath '" << filepath << "' " << hex_result.str() << endl;
  55. }else {
  56. log << "could not alloc memory" << endl;
  57. }
  58. file.close();
  59. } else {
  60. log << "file '"<< filepath << "' could not be opened" << endl;
  61. }
  62. return hex_result.str();
  63. }
  64. oxum_t Checksum::oxum_of_file(const string& filepath) {
  65. ifstream file (filepath, ios::ate);
  66. oxum_t oxum{};
  67. //log << "processing file '" << filepath << "'" << endl;
  68. if (file.is_open() ) {
  69. ifstream::pos_type fileSize;
  70. fileSize = file.tellg();
  71. oxum.octetcount = fileSize;
  72. oxum.streamcount = 1;
  73. file.close();
  74. } else {
  75. log << "file '"<< filepath << "' could not be opened" << endl;
  76. }
  77. return oxum;
  78. }
  79. oxum_t Checksum::oxum_of_filelist( list<string> files) {
  80. oxum_t oxum{};
  81. oxum.octetcount=0;
  82. oxum.streamcount=0;
  83. list<string>::iterator i;
  84. for (i=files.begin(); i!= files.end(); ++i) {
  85. oxum_t tmp = this->oxum_of_file( *i );
  86. oxum.octetcount+= tmp.octetcount;
  87. oxum.streamcount+= tmp.streamcount;
  88. }
  89. return oxum;
  90. }
  91. void Checksum::get_logstream( stringstream & log ) {
  92. log << this->log.rdbuf();
  93. }
  94. void Checksum::reset_logstream() {
  95. this->log.str(std::string());
  96. }
  97. // vim: set tabstop=4 softtabstop=0 expandtab shiftwidth=4 smarttab