1 #include "logger.hpp" 2 3 #include <sstream> 4 5 namespace vpd 6 { 7 std::shared_ptr<Logger> Logger::m_loggerInstance; 8 9 void Logger::logMessage(std::string_view i_message, 10 const PlaceHolder& i_placeHolder, 11 const types::PelInfoTuple* i_pelTuple, 12 const std::source_location& i_location) 13 { 14 std::ostringstream l_log; 15 l_log << "FileName: " << i_location.file_name() << "," 16 << " Line: " << i_location.line() << " " << i_message; 17 18 if ((i_placeHolder == PlaceHolder::COLLECTION) && m_collectionLogger) 19 { 20 // Log it to a specific place. 21 m_collectionLogger->logMessage(l_log.str()); 22 } 23 else if (i_placeHolder == PlaceHolder::PEL) 24 { 25 if (i_pelTuple) 26 { 27 // LOG PEL 28 // This should call create PEL API from the event logger. 29 return; 30 } 31 std::cout << "Pel info tuple required to log PEL for message <" + 32 l_log.str() + ">" 33 << std::endl; 34 } 35 else if ((i_placeHolder == PlaceHolder::VPD_WRITE) && m_vpdWriteLogger) 36 { 37 m_vpdWriteLogger->logMessage(l_log.str()); 38 } 39 else 40 { 41 // Default case, let it go to journal. 42 std::cout << l_log.str() << std::endl; 43 } 44 } 45 46 void Logger::initiateVpdCollectionLogging() noexcept 47 { 48 try 49 { 50 /* TODO: 51 - check /var/lib/vpd for number "collection.*" log file 52 - if 3 collection_[0-2].log files are found 53 - delete collection_1.log 54 - create collection logger object with collection_1.log 55 parameter 56 - else 57 - create collection logger object with collection_(n+1).log 58 parameter*/ 59 m_collectionLogger.reset( 60 new AsyncFileLogger("/var/lib/vpd/collection.log", 512)); 61 } 62 catch (const std::exception& l_ex) 63 { 64 logMessage("Failed to initialize collection logger. Error: " + 65 std::string(l_ex.what())); 66 } 67 } 68 69 void SyncFileLogger::logMessage(const std::string_view& i_message) 70 { 71 try 72 { 73 if (++m_currentNumEntries > m_maxEntries) 74 { 75 rotateFile(); 76 } 77 m_fileStream << timestamp() << " : " << i_message << std::endl; 78 } 79 catch (const std::exception& l_ex) 80 { 81 // log message to journal if we fail to log to file 82 auto l_logger = Logger::getLoggerInstance(); 83 l_logger->logMessage(i_message); 84 } 85 } 86 87 void AsyncFileLogger::logMessage( 88 [[maybe_unused]] const std::string_view& i_message) 89 { 90 try 91 { 92 /* TODO: 93 - acquire lock on queue 94 - push message to queue 95 - notify log worker thread 96 */ 97 } 98 catch (const std::exception& l_ex) 99 { 100 auto l_logger = Logger::getLoggerInstance(); 101 l_logger->logMessage(i_message); 102 } 103 } 104 105 void AsyncFileLogger::fileWorker() noexcept 106 { 107 /* TODO: 108 - start an infinite loop 109 - check exit conditions and exit if needed 110 - wait for notification from log producer 111 - if notification received, flush the messages from queue to file 112 - rotate file if needed 113 */ 114 } 115 116 void ILogFileHandler::rotateFile( 117 [[maybe_unused]] const unsigned i_numEntriesToDelete) 118 { 119 /* TODO: 120 - delete specified number of oldest entries from beginning of file 121 - rewrite file to move existing logs to beginning of file 122 */ 123 m_currentNumEntries = m_maxEntries - i_numEntriesToDelete; 124 } 125 namespace logging 126 { 127 void logMessage(std::string_view message, const std::source_location& location) 128 { 129 std::ostringstream log; 130 log << "FileName: " << location.file_name() << "," 131 << " Line: " << location.line() << " " << message; 132 133 std::cout << log.str() << std::endl; 134 } 135 } // namespace logging 136 } // namespace vpd 137