auto_roll_logger.h 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164
  1. // Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
  2. // This source code is licensed under both the GPLv2 (found in the
  3. // COPYING file in the root directory) and Apache 2.0 License
  4. // (found in the LICENSE.Apache file in the root directory).
  5. //
  6. // Logger implementation that can be shared by all environments
  7. // where enough posix functionality is available.
  8. #pragma once
  9. #include <list>
  10. #include <queue>
  11. #include <string>
  12. #include "file/filename.h"
  13. #include "port/port.h"
  14. #include "port/util_logger.h"
  15. #include "test_util/sync_point.h"
  16. #include "util/mutexlock.h"
  17. namespace ROCKSDB_NAMESPACE {
  18. #ifndef ROCKSDB_LITE
  19. // Rolls the log file by size and/or time
  20. class AutoRollLogger : public Logger {
  21. public:
  22. AutoRollLogger(Env* env, const std::string& dbname,
  23. const std::string& db_log_dir, size_t log_max_size,
  24. size_t log_file_time_to_roll, size_t keep_log_file_num,
  25. const InfoLogLevel log_level = InfoLogLevel::INFO_LEVEL);
  26. using Logger::Logv;
  27. void Logv(const char* format, va_list ap) override;
  28. // Write a header entry to the log. All header information will be written
  29. // again every time the log rolls over.
  30. virtual void LogHeader(const char* format, va_list ap) override;
  31. // check if the logger has encountered any problem.
  32. Status GetStatus() {
  33. return status_;
  34. }
  35. size_t GetLogFileSize() const override {
  36. if (!logger_) {
  37. return 0;
  38. }
  39. std::shared_ptr<Logger> logger;
  40. {
  41. MutexLock l(&mutex_);
  42. // pin down the current logger_ instance before releasing the mutex.
  43. logger = logger_;
  44. }
  45. return logger->GetLogFileSize();
  46. }
  47. void Flush() override {
  48. std::shared_ptr<Logger> logger;
  49. {
  50. MutexLock l(&mutex_);
  51. // pin down the current logger_ instance before releasing the mutex.
  52. logger = logger_;
  53. }
  54. TEST_SYNC_POINT("AutoRollLogger::Flush:PinnedLogger");
  55. if (logger) {
  56. logger->Flush();
  57. }
  58. }
  59. virtual ~AutoRollLogger() {
  60. if (logger_ && !closed_) {
  61. logger_->Close();
  62. }
  63. }
  64. using Logger::GetInfoLogLevel;
  65. InfoLogLevel GetInfoLogLevel() const override {
  66. MutexLock l(&mutex_);
  67. if (!logger_) {
  68. return Logger::GetInfoLogLevel();
  69. }
  70. return logger_->GetInfoLogLevel();
  71. }
  72. using Logger::SetInfoLogLevel;
  73. void SetInfoLogLevel(const InfoLogLevel log_level) override {
  74. MutexLock lock(&mutex_);
  75. Logger::SetInfoLogLevel(log_level);
  76. if (logger_) {
  77. logger_->SetInfoLogLevel(log_level);
  78. }
  79. }
  80. void SetCallNowMicrosEveryNRecords(uint64_t call_NowMicros_every_N_records) {
  81. call_NowMicros_every_N_records_ = call_NowMicros_every_N_records;
  82. }
  83. // Expose the log file path for testing purpose
  84. std::string TEST_log_fname() const {
  85. return log_fname_;
  86. }
  87. uint64_t TEST_ctime() const { return ctime_; }
  88. Logger* TEST_inner_logger() const { return logger_.get(); }
  89. protected:
  90. // Implementation of Close()
  91. virtual Status CloseImpl() override {
  92. if (logger_) {
  93. return logger_->Close();
  94. } else {
  95. return Status::OK();
  96. }
  97. }
  98. private:
  99. bool LogExpired();
  100. Status ResetLogger();
  101. void RollLogFile();
  102. // Read all names of old log files into old_log_files_
  103. // If there is any error, put the error code in status_
  104. void GetExistingFiles();
  105. // Delete old log files if it excceeds the limit.
  106. Status TrimOldLogFiles();
  107. // Log message to logger without rolling
  108. void LogInternal(const char* format, ...);
  109. // Serialize the va_list to a string
  110. std::string ValistToString(const char* format, va_list args) const;
  111. // Write the logs marked as headers to the new log file
  112. void WriteHeaderInfo();
  113. std::string log_fname_; // Current active info log's file name.
  114. std::string dbname_;
  115. std::string db_log_dir_;
  116. std::string db_absolute_path_;
  117. Env* env_;
  118. std::shared_ptr<Logger> logger_;
  119. // current status of the logger
  120. Status status_;
  121. const size_t kMaxLogFileSize;
  122. const size_t kLogFileTimeToRoll;
  123. const size_t kKeepLogFileNum;
  124. // header information
  125. std::list<std::string> headers_;
  126. // List of all existing info log files. Used for enforcing number of
  127. // info log files.
  128. // Full path is stored here. It consumes signifianctly more memory
  129. // than only storing file name. Can optimize if it causes a problem.
  130. std::queue<std::string> old_log_files_;
  131. // to avoid frequent env->NowMicros() calls, we cached the current time
  132. uint64_t cached_now;
  133. uint64_t ctime_;
  134. uint64_t cached_now_access_count;
  135. uint64_t call_NowMicros_every_N_records_;
  136. mutable port::Mutex mutex_;
  137. };
  138. #endif // !ROCKSDB_LITE
  139. // Facade to craete logger automatically
  140. Status CreateLoggerFromOptions(const std::string& dbname,
  141. const DBOptions& options,
  142. std::shared_ptr<Logger>* logger);
  143. } // namespace ROCKSDB_NAMESPACE