Utility.cpp 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119
  1. #include "core/utils/Utility.hpp"
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <string.h>
  5. #include "ErrorSimulator.hpp"
  6. #include "core/utils/Error.hpp"
  7. #include "core/utils/Logger.hpp"
  8. static Core::ExitHandler exitHandler = nullptr;
  9. static void* exitData = nullptr;
  10. static Core::OutOfMemoryHandler outOfMemoryHandler = nullptr;
  11. static void* outOfMemoryData = nullptr;
  12. void Core::exitWithHandler(const char* file, int line, int value) {
  13. if(value != 0) {
  14. printf("%sExit from %s:%d with value %d%s\n", Core::Logger::COLOR_RED,
  15. Core::Logger::getFileName(file), line, value,
  16. Core::Logger::COLOR_RESET);
  17. }
  18. if(exitHandler != nullptr) {
  19. exitHandler(value, exitData);
  20. }
  21. exit(value);
  22. }
  23. void Core::setExitHandler(ExitHandler eh, void* data) {
  24. exitHandler = eh;
  25. exitData = data;
  26. }
  27. #define CORE_TO_STRING(type, cast, format) \
  28. CError Core::toString(type t, char* buffer, size_t size) { \
  29. int w = snprintf(buffer, size, format, static_cast<cast>(t)); \
  30. if(w < 0) { \
  31. return ErrorCode::ERROR; \
  32. } \
  33. return static_cast<size_t>(w) >= size ? ErrorCode::CAPACITY_REACHED \
  34. : ErrorCode::NONE; \
  35. }
  36. CORE_TO_STRING(signed short, signed short, "%hd")
  37. CORE_TO_STRING(unsigned short, unsigned short, "%hu")
  38. CORE_TO_STRING(signed int, signed int, "%d")
  39. CORE_TO_STRING(unsigned int, unsigned int, "%u")
  40. CORE_TO_STRING(signed long, signed long, "%ld")
  41. CORE_TO_STRING(unsigned long, unsigned long, "%lu")
  42. CORE_TO_STRING(signed long long, signed long long, "%lld")
  43. CORE_TO_STRING(unsigned long long, unsigned long long, "%llu")
  44. CORE_TO_STRING(float, double, "%.2f")
  45. CORE_TO_STRING(double, double, "%.2lf")
  46. CORE_TO_STRING(long double, long double, "%.2Lf")
  47. void Core::print(int c) {
  48. if(putchar(c) < 0) {
  49. CORE_EXIT(static_cast<int>(ErrorCode::BLOCKED_STDOUT));
  50. }
  51. }
  52. void Core::print(const char* s) {
  53. if(fputs(s, stdout) < 0) {
  54. CORE_EXIT(static_cast<int>(ErrorCode::BLOCKED_STDOUT));
  55. }
  56. }
  57. void Core::printLine(const char* s) {
  58. if(puts(s) < 0) {
  59. CORE_EXIT(static_cast<int>(ErrorCode::BLOCKED_STDOUT));
  60. }
  61. }
  62. void Core::setOutOfMemoryHandler(OutOfMemoryHandler h, void* data) {
  63. outOfMemoryHandler = h;
  64. outOfMemoryData = data;
  65. }
  66. void* Core::allocate(size_t n) {
  67. void* p = malloc(n);
  68. #ifdef ERROR_SIMULATOR
  69. if(CORE_ALLOC_FAIL && p != nullptr) {
  70. free(p);
  71. p = nullptr;
  72. }
  73. #endif
  74. while(p == nullptr && outOfMemoryHandler != nullptr) {
  75. outOfMemoryHandler(outOfMemoryData);
  76. p = malloc(n);
  77. }
  78. if(p == nullptr) {
  79. CORE_EXIT(static_cast<int>(ErrorCode::OUT_OF_MEMORY));
  80. }
  81. return p;
  82. }
  83. void* Core::reallocate(void* oldP, size_t n) {
  84. if(n <= 0) {
  85. free(oldP);
  86. return nullptr;
  87. }
  88. void* p = realloc(oldP, n);
  89. #ifdef ERROR_SIMULATOR
  90. if(CORE_ALLOC_FAIL && p != nullptr) {
  91. oldP = p;
  92. p = nullptr;
  93. }
  94. #endif
  95. // this double check is to prevent the compiler from complaining
  96. if(p == nullptr) {
  97. while(p == nullptr && outOfMemoryHandler != nullptr) {
  98. outOfMemoryHandler(outOfMemoryData);
  99. p = realloc(oldP, n);
  100. }
  101. }
  102. if(p == nullptr) {
  103. CORE_EXIT(static_cast<int>(ErrorCode::OUT_OF_MEMORY));
  104. }
  105. return p;
  106. }