Nelze vybrat více než 25 témat Téma musí začínat písmenem nebo číslem, může obsahovat pomlčky („-“) a může být dlouhé až 35 znaků.

TestFileBackup.cpp 7.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294
  1. // $Id$
  2. //
  3. // \file TestFileBackup.cpp
  4. //
  5. // Copyright (C) 2012, ARM Research Labs, LLC.
  6. // See www.armresearch.com for the copyright terms.
  7. //
  8. // This is the unit test for the class FileBackup.
  9. //
  10. #include <iostream>
  11. #include <fstream>
  12. #include <sstream>
  13. #include <vector>
  14. #include <stdexcept>
  15. #include <map>
  16. #include <cstdlib>
  17. #include <cstring>
  18. #include <cerrno>
  19. #include "FileBackup.hpp"
  20. /// Output error.
  21. #define Error(msg) \
  22. { \
  23. std::cerr << "In file " << __FILE__ << ":" << __LINE__ << ": "; \
  24. std::cerr << msg; \
  25. }
  26. /// Exit with error.
  27. #define ErrorExit(msg) \
  28. { \
  29. Error(msg) \
  30. std::exit(-1); \
  31. }
  32. /// Vector of strings
  33. typedef std::vector<std::string> StringContainer;
  34. /// Names of files to back up.
  35. StringContainer FileName;
  36. /// Container for the file content.
  37. typedef std::map<std::string, std::string> ContentContainer;
  38. /// Content of files to back up.
  39. ContentContainer FileContent;
  40. /// Random characters.
  41. const std::string RandomChar("abcdefghijklmnopqustuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ!@#$%^&*()_+|=-");
  42. std::string::size_type CharLen = RandomChar.length();
  43. /// Unit under test.
  44. FileBackup TestFileBackup;
  45. /// Initialize test input.
  46. void
  47. Initialize() {
  48. std::vector<int> FileSize;
  49. FileName.push_back("File1.txt");
  50. FileSize.push_back(1024);
  51. FileName.push_back("File2.txt");
  52. FileSize.push_back(4000);
  53. FileName.push_back("File3.txt");
  54. FileSize.push_back(493);
  55. FileName.push_back("File4.txt");
  56. FileSize.push_back(203043);
  57. const char *CharPtr = RandomChar.data();
  58. std::vector<int>::iterator iSize = FileSize.begin();
  59. for (StringContainer::iterator iFile = FileName.begin(); // Create random data.
  60. iFile != FileName.end();
  61. iFile++, iSize++) {
  62. for (int iChar = 0; iChar < *iSize; iChar++) {
  63. FileContent[*iFile].push_back(RandomChar[static_cast<std::size_t>(std::rand() * (1.0 / (RAND_MAX + 1.0 )) * CharLen)]);
  64. }
  65. remove(iFile->c_str());
  66. remove(FileBackup::GetBackupFileName(*iFile).c_str());
  67. std::ofstream Output; // Write the test file.
  68. Output.open(iFile->c_str(), std::ios::trunc);
  69. if (!Output) {
  70. std::string Temp;
  71. Temp = "Initialize: Error opening the test file " + *iFile;
  72. Temp += " to copy to: ";
  73. Temp += strerror(errno);
  74. throw std::runtime_error(Temp);
  75. }
  76. Output << FileContent[*iFile];
  77. if (Output.bad() || Output.fail()) {
  78. std::string Temp;
  79. Temp = "Initialize: Error writing the test file " + *iFile;
  80. Temp += ": ";
  81. Temp += strerror(errno);
  82. throw std::runtime_error(Temp);
  83. }
  84. Output.close();
  85. }
  86. }
  87. bool
  88. TestBackupRestore() {
  89. for (int i = 0; i < FileName.size(); i++) { // Back up and overwrite the files.
  90. TestFileBackup.CreateBackupFile(FileName[i]);
  91. std::ofstream Output;
  92. Output.open(FileName[i].c_str(), std::ios::trunc); // Overwrite the test file.
  93. if (!Output) {
  94. std::string Temp;
  95. Temp = "TestBackupRestore: Error opening the test file " + FileName[i];
  96. Temp += " to overwrite: ";
  97. Temp += strerror(errno);
  98. throw std::runtime_error(Temp);
  99. }
  100. for (int j = 0; j < 223; j++) {
  101. Output << RandomChar[static_cast<std::size_t>(std::rand() * (1.0 / (RAND_MAX + 1.0 )) * CharLen)];
  102. }
  103. if (Output.bad() || Output.fail()) {
  104. std::string Temp;
  105. Temp = "TestBackupRestore: Error overwriting the test file " + FileName[i];
  106. Temp += ": ";
  107. Temp += strerror(errno);
  108. throw std::runtime_error(Temp);
  109. }
  110. Output.close();
  111. }
  112. TestFileBackup.RestoreAllFilesFromBackup();
  113. bool ResultIsPass = true;
  114. for (int i = 0; i < FileName.size(); i++) { // Check content of restored files.
  115. std::ifstream Input;
  116. Input.open(FileName[i].c_str());
  117. if (!Input) {
  118. std::string Temp;
  119. Temp = "TestBackupRestore: Error opening the restored file " + FileName[i];
  120. Temp += ": ";
  121. Temp += strerror(errno);
  122. throw std::runtime_error(Temp);
  123. }
  124. std::string RestoredContent;
  125. Input >> RestoredContent;
  126. Input.close();
  127. if (!Input) {
  128. std::string Temp;
  129. Temp = "TestBackupRestore: Error closing the restored file " + FileName[i];
  130. Temp += ": ";
  131. Temp += strerror(errno);
  132. throw std::runtime_error(Temp);
  133. }
  134. if (RestoredContent != FileContent[FileName[i]]) {
  135. std::string Temp;
  136. Temp = "***Error--File " + FileName[i];
  137. Temp += " was not restored correctly.\n";
  138. Error(Temp);
  139. ResultIsPass = false;
  140. }
  141. }
  142. return ResultIsPass;
  143. }
  144. bool
  145. TestRemoveAllBackupFiles() {
  146. TestFileBackup.RemoveAllBackupFiles();
  147. bool ResultIsPass = true;
  148. for (int i = 0; i < FileName.size(); i++) { // Check that files don't exist.
  149. std::ifstream Input;
  150. std::string BackupFileName;
  151. BackupFileName = FileBackup::GetBackupFileName(FileName[i]);
  152. Input.open(BackupFileName.c_str());
  153. Input.close();
  154. if (Input) {
  155. std::string Temp;
  156. Temp = "***Error--Backup file " + BackupFileName;
  157. Temp += " was not removed.\n";
  158. Error(Temp);
  159. ResultIsPass = false;
  160. }
  161. }
  162. return ResultIsPass;
  163. }
  164. void
  165. Finalize() {
  166. for (int i = 0; i < FileName.size(); i++) {
  167. remove(FileName[i].c_str());
  168. }
  169. }
  170. /// Unit tests for FileBackup.
  171. //
  172. // This function creates several files of varying size, and verifies
  173. // the functionality of the FileBackup backup, restore, and delete
  174. // functions.
  175. //
  176. int main(int argc, char* argv[]) {
  177. try { // Catch anything that breaks loose.
  178. Initialize(); // Create test files.
  179. // Test backup/restore.
  180. if (!TestBackupRestore()) {
  181. ErrorExit("TestBackupRestore() failure.\n");
  182. }
  183. // Test cleanup.
  184. if (!TestRemoveAllBackupFiles()) {
  185. ErrorExit("TestRemoveAllBackupFiles() failure.\n");
  186. }
  187. Finalize(); // Remove test files.
  188. } // That's all folks.
  189. catch(std::exception& e) { // Report any normal exceptions.
  190. std::cerr << "FileBackup exception: " << e.what() << std::endl;
  191. return -1;
  192. }
  193. catch(...) { // Report any unexpected exceptions.
  194. std::cerr << "Panic! Unknown Exception!" << std::endl;
  195. return -1;
  196. }
  197. return 0; // Normally we return zero.
  198. }