From 3bbe41aad624506577b728efc98bf30a7406d700 Mon Sep 17 00:00:00 2001 From: "stefan@webrtc.org" Date: Wed, 7 Sep 2011 15:31:03 +0000 Subject: [PATCH] Add support for a numeric table id in DataLogs. Useful when logging in modules which have multiple instances and the logs should be separated into different tables. Review URL: http://webrtc-codereview.appspot.com/132003 git-svn-id: http://webrtc.googlecode.com/svn/trunk@555 4adac7df-926f-26a2-2b94-8c16560cd09d --- src/system_wrappers/interface/data_log.h | 29 ++++---- src/system_wrappers/interface/data_log_impl.h | 40 ++++------ src/system_wrappers/source/data_log.cc | 31 +++++--- src/system_wrappers/source/data_log_dummy.cc | 6 +- .../source/data_log_unittest.cc | 74 +++++++++---------- 5 files changed, 89 insertions(+), 91 deletions(-) diff --git a/src/system_wrappers/interface/data_log.h b/src/system_wrappers/interface/data_log.h index 4771f21ff..6fc1d6449 100644 --- a/src/system_wrappers/interface/data_log.h +++ b/src/system_wrappers/interface/data_log.h @@ -53,26 +53,29 @@ class DataLog { // CreateLog or memory leak will occur. static void ReturnLog(); - // Adds a new table, with the name table_name, and creates the file, with - // the name file_name, to which the table will be written. - // table_name is case sensitive. - static int AddTable(const std::string& table_name, - const std::string& file_name); + // Combines the string table_name and the integer table_id into a new string + // table_name + _ + table_id. The new string will be lower-case. + static std::string Combine(const std::string& table_name, int table_id); + + // Adds a new table, with the name table_name, and creates the file, with the + // name table_name + ".txt", to which the table will be written. + // table_name is treated in a case sensitive way. + static int AddTable(const std::string& table_name); // Adds a new column to a table. The column will be a multi-value-column // if multi_value_length is greater than 1. - // Both table_name and column_name are case sensitive. + // table_name and column_name are treated in a case sensitive way. static int AddColumn(const std::string& table_name, const std::string& column_name, int multi_value_length); - // Inserts a single value into a table with name table_name at the column - // with name column_name. + // Inserts a single value into a table with name table_name at the column with + // name column_name. // Note that the ValueContainer makes use of the copy constructor, // operator= and operator<< of the type T, and that the template type must // implement a deep copy copy constructor and operator=. // Copy constructor and operator= must not be disabled for the type T. - // Both table_name and column_name are case sensitive. + // table_name and column_name are treated in a case sensitive way. template static int InsertCell(const std::string& table_name, const std::string& column_name, @@ -92,7 +95,7 @@ class DataLog { // operator= and operator<< of the type T, and that the template type // must implement a deep copy copy constructor and operator=. // Copy constructor and operator= must not be disabled for the type T. - // Both table_name and column_name are case sensitive. + // table_name and column_name are treated in a case sensitive way. template static int InsertCell(const std::string& table_name, const std::string& column_name, @@ -107,9 +110,9 @@ class DataLog { new MultiValueContainer(array, length)); } - // For the table table_name: Writes the current row to file. Starts a new - // empty row. - // table_name is case sensitive. + // For the table with name table_name: Writes the current row to file. + // Starts a new empty row. + // table_name is treated in a case-sensitive way. static int NextRow(const std::string& table_name); }; diff --git a/src/system_wrappers/interface/data_log_impl.h b/src/system_wrappers/interface/data_log_impl.h index 67fc5486d..cef496453 100644 --- a/src/system_wrappers/interface/data_log_impl.h +++ b/src/system_wrappers/interface/data_log_impl.h @@ -83,47 +83,37 @@ class DataLogImpl { public: ~DataLogImpl(); - // Creates a log which uses a separate thread (referred to as the file - // writer thread) for writing log rows to file. - // - // Calls to this function after the log object has been created will only - // increment the reference counter. + // The implementation of the CreateLog() method declared in data_log.h. + // See data_log.h for a description. static int CreateLog(); - // Returns a pointer to the instance of DataLogImpl which was created by - // CreateLog(), or NULL if no instance has been created, or if the - // previous instance has been deleted. + // The implementation of the StaticInstance() method declared in data_log.h. + // See data_log.h for a description. static DataLogImpl* StaticInstance(); - // Decrements the reference counter keeping track of the number of times - // CreateLog() has been called. When the reference counter reaches 0 - // the DataLogImpl instance created by CreateLog() will be deleted. - // Should be called equal number of times as successful calls to - // CreateLog or memory leak will occur. + // The implementation of the ReturnLog() method declared in data_log.h. See + // data_log.h for a description. static void ReturnLog(); - // Adds a new table, with the name table_name, and creates the file, with - // the name file_name, to which the table will be written. - // table_name is case sensitive. - int AddTable(const std::string& table_name, const std::string& file_name); + // The implementation of the AddTable() method declared in data_log.h. See + // data_log.h for a description. + int AddTable(const std::string& table_name); - // Adds a new column to a table. The column will be a multi-value-column - // if multi_value_length is greater than 1. - // Both table_name and column_name are case sensitive. + // The implementation of the AddColumn() method declared in data_log.h. See + // data_log.h for a description. int AddColumn(const std::string& table_name, const std::string& column_name, int multi_value_length); // Inserts a Container into a table with name table_name at the column // with name column_name. - // Both table_name and column_name are case sensitive. + // column_name is treated in a case sensitive way. int InsertCell(const std::string& table_name, const std::string& column_name, const Container* value_container); - // For the table table_name: Writes the current row to file. Starts a new - // empty row. - // table_name is case sensitive. + // The implementation of the NextRow() method declared in data_log.h. See + // data_log.h for a description. int NextRow(const std::string& table_name); private: @@ -149,7 +139,7 @@ class DataLogImpl { // Stops the continuous calling of Process(). void StopThread(); - // Collection of tables indexed by table name as std::string + // Collection of tables indexed by the table name as std::string. typedef std::map TableMap; typedef webrtc::scoped_ptr CritSectScopedPtr; diff --git a/src/system_wrappers/source/data_log.cc b/src/system_wrappers/source/data_log.cc index 805f68c19..c33f24c47 100644 --- a/src/system_wrappers/source/data_log.cc +++ b/src/system_wrappers/source/data_log.cc @@ -12,6 +12,7 @@ #include +#include #include #include "critical_section_wrapper.h" @@ -28,7 +29,7 @@ DataLogImpl::CritSectScopedPtr DataLogImpl::crit_sect_( DataLogImpl* DataLogImpl::instance_ = NULL; // A Row contains cells, which are indexed by the column names as std::string. -// The string index is case sensitive. +// The string index is treated in a case sensitive way. class Row { public: Row(); @@ -36,13 +37,13 @@ class Row { // Inserts a Container into the cell of the column specified with // column_name. - // column_name is case sensitive. + // column_name is treated in a case sensitive way. int InsertCell(const std::string& column_name, const Container* value_container); // Converts the value at the column specified by column_name to a string // stored in value_string. - // column_name is case sensitive. + // column_name is treated in a case sensitive way. void ToString(const std::string& column_name, std::string* value_string); private: @@ -64,7 +65,7 @@ class LogTable { // Adds the column with name column_name to the table. The column will be a // multi-value-column if multi_value_length is greater than 1. - // column_name is case sensitive. + // column_name is treated in a case sensitive way. int AddColumn(const std::string& column_name, int multi_value_length); // Buffers the current row while it is waiting to be written to file, @@ -74,7 +75,7 @@ class LogTable { // Inserts a Container into the cell of the column specified with // column_name. - // column_name is case sensitive. + // column_name is treated in a case sensitive way. int InsertCell(const std::string& column_name, const Container* value_container); @@ -280,12 +281,21 @@ void DataLog::ReturnLog() { return DataLogImpl::ReturnLog(); } -int DataLog::AddTable(const std::string& table_name, - const std::string& file_name) { +std::string DataLog::Combine(const std::string& table_name, int table_id) { + std::stringstream ss; + std::string combined_id; + ss << table_name << "_" << table_id; + ss >> combined_id; + std::transform(combined_id.begin(), combined_id.end(), combined_id.begin(), + ::tolower); + return combined_id; +} + +int DataLog::AddTable(const std::string& table_name) { DataLogImpl* data_log = DataLogImpl::StaticInstance(); if (data_log == NULL) return -1; - return data_log->AddTable(table_name, file_name); + return data_log->AddTable(table_name); } int DataLog::AddColumn(const std::string& table_name, @@ -367,14 +377,13 @@ void DataLogImpl::ReturnLog() { instance_ = NULL; } -int DataLogImpl::AddTable(const std::string& table_name, - const std::string& file_name) { +int DataLogImpl::AddTable(const std::string& table_name) { WriteLockScoped synchronize(*tables_lock_); // Make sure we don't add a table which already exists if (tables_.count(table_name) > 0) return -1; tables_[table_name] = new LogTable(); - if (tables_[table_name]->CreateLogFile(file_name) == -1) + if (tables_[table_name]->CreateLogFile(table_name + ".txt") == -1) return -1; return 0; } diff --git a/src/system_wrappers/source/data_log_dummy.cc b/src/system_wrappers/source/data_log_dummy.cc index 21837aed9..3cd177a33 100644 --- a/src/system_wrappers/source/data_log_dummy.cc +++ b/src/system_wrappers/source/data_log_dummy.cc @@ -19,8 +19,7 @@ int DataLog::CreateLog() { void DataLog::ReturnLog() { } -int DataLog::AddTable(const std::string& /*table_name*/, - const std::string& /*file_name*/) { +int DataLog::AddTable(const std::string& /*table_name*/) { return 0; } @@ -47,8 +46,7 @@ DataLogImpl* DataLogImpl::StaticInstance() { void DataLogImpl::ReturnLog() { } -int DataLogImpl::AddTable(const std::string& /*table_name*/, - const std::string& /*file_name*/) { +int DataLogImpl::AddTable(const std::string& /*table_name*/) { return 0; } diff --git a/src/system_wrappers/source/data_log_unittest.cc b/src/system_wrappers/source/data_log_unittest.cc index 60318a77a..945823466 100644 --- a/src/system_wrappers/source/data_log_unittest.cc +++ b/src/system_wrappers/source/data_log_unittest.cc @@ -113,29 +113,30 @@ class DataLogParser { TEST(TestDataLog, CreateReturnTest) { for (int i = 0; i < 10; ++i) ASSERT_EQ(DataLog::CreateLog(), 0); - ASSERT_EQ(DataLog::AddTable("a proper table", "table.txt"), 0); + ASSERT_EQ(DataLog::AddTable(DataLog::Combine("a proper table", 1)), 0); for (int i = 0; i < 10; ++i) DataLog::ReturnLog(); - ASSERT_LT(DataLog::AddTable("table failure", "table.txt"), 0); + ASSERT_LT(DataLog::AddTable(DataLog::Combine("table failure", 1)), 0); } TEST(TestDataLog, VerifySingleTable) { DataLog::CreateLog(); - DataLog::AddTable("table1", "table1.txt"); - DataLog::AddColumn("table1", "arrival", 1); - DataLog::AddColumn("table1", "timestamp", 1); - DataLog::AddColumn("table1", "size", 5); + DataLog::AddTable(DataLog::Combine("table", 1)); + DataLog::AddColumn(DataLog::Combine("table", 1), "arrival", 1); + DataLog::AddColumn(DataLog::Combine("table", 1), "timestamp", 1); + DataLog::AddColumn(DataLog::Combine("table", 1), "size", 5); WebRtc_UWord32 sizes[5] = {1400, 1500, 1600, 1700, 1800}; for (int i = 0; i < 10; ++i) { - DataLog::InsertCell("table1", "arrival", static_cast(i)); - DataLog::InsertCell("table1", "timestamp", + DataLog::InsertCell(DataLog::Combine("table", 1), "arrival", + static_cast(i)); + DataLog::InsertCell(DataLog::Combine("table", 1), "timestamp", static_cast(4354 + i)); - DataLog::InsertCell("table1", "size", sizes, 5); - DataLog::NextRow("table1"); + DataLog::InsertCell(DataLog::Combine("table", 1), "size", sizes, 5); + DataLog::NextRow(DataLog::Combine("table", 1)); } DataLog::ReturnLog(); // Verify file - FILE* table = fopen("table1.txt", "r"); + FILE* table = fopen("table_1.txt", "r"); ASSERT_FALSE(table == NULL); // Read the column names and verify with the expected columns. // Note that the columns are written to file in alphabetical order. @@ -170,31 +171,31 @@ TEST(TestDataLog, VerifySingleTable) { TEST(TestDataLog, VerifyMultipleTables) { DataLog::CreateLog(); - DataLog::AddTable("table2", "table2.txt"); - DataLog::AddTable("table3", "table3.txt"); - DataLog::AddColumn("table2", "arrival", 1); - DataLog::AddColumn("table2", "timestamp", 1); - DataLog::AddColumn("table2", "size", 1); - DataLog::AddTable("table4", "table4.txt"); - DataLog::AddColumn("table3", "timestamp", 1); - DataLog::AddColumn("table3", "arrival", 1); - DataLog::AddColumn("table4", "size", 1); + DataLog::AddTable(DataLog::Combine("table", 2)); + DataLog::AddTable(DataLog::Combine("table", 3)); + DataLog::AddColumn(DataLog::Combine("table", 2), "arrival", 1); + DataLog::AddColumn(DataLog::Combine("table", 2), "timestamp", 1); + DataLog::AddColumn(DataLog::Combine("table", 2), "size", 1); + DataLog::AddTable(DataLog::Combine("table", 4)); + DataLog::AddColumn(DataLog::Combine("table", 3), "timestamp", 1); + DataLog::AddColumn(DataLog::Combine("table", 3), "arrival", 1); + DataLog::AddColumn(DataLog::Combine("table", 4), "size", 1); for (WebRtc_Word32 i = 0; i < 10; ++i) { - DataLog::InsertCell("table2", "arrival", + DataLog::InsertCell(DataLog::Combine("table", 2), "arrival", static_cast(i)); - DataLog::InsertCell("table2", "timestamp", + DataLog::InsertCell(DataLog::Combine("table", 2), "timestamp", static_cast(4354 + i)); - DataLog::InsertCell("table2", "size", + DataLog::InsertCell(DataLog::Combine("table", 2), "size", static_cast(1200 + 10 * i)); - DataLog::InsertCell("table3", "timestamp", + DataLog::InsertCell(DataLog::Combine("table", 3), "timestamp", static_cast(4354 + i)); - DataLog::InsertCell("table3", "arrival", + DataLog::InsertCell(DataLog::Combine("table", 3), "arrival", static_cast(i)); - DataLog::InsertCell("table4", "size", + DataLog::InsertCell(DataLog::Combine("table", 4), "size", static_cast(1200 + 10 * i)); - DataLog::NextRow("table4"); - DataLog::NextRow("table2"); - DataLog::NextRow("table3"); + DataLog::NextRow(DataLog::Combine("table", 4)); + DataLog::NextRow(DataLog::Combine("table", 2)); + DataLog::NextRow(DataLog::Combine("table", 3)); } DataLog::ReturnLog(); @@ -217,7 +218,7 @@ TEST(TestDataLog, VerifyMultipleTables) { // Verify table 2 { - FILE* table = fopen("table2.txt", "r"); + FILE* table = fopen("table_2.txt", "r"); ASSERT_FALSE(table == NULL); ExpectedValuesMap expected; expected["arrival,"] = ExpectedValues( @@ -240,20 +241,18 @@ TEST(TestDataLog, VerifyMultipleTables) { // Verify table 3 { - FILE* table = fopen("table3.txt", "r"); + FILE* table = fopen("table_3.txt", "r"); ASSERT_FALSE(table == NULL); ExpectedValuesMap expected; expected["arrival,"] = ExpectedValues( std::vector(string_arrival, string_arrival + - sizeof(string_arrival) - / sizeof(std::string)), + kNumberOfRows), 1); expected["timestamp,"] = ExpectedValues( std::vector(string_timestamp, string_timestamp + - sizeof(string_timestamp) / - sizeof(std::string)), + kNumberOfRows), 1); ASSERT_EQ(DataLogParser::VerifyTable(table, expected), 0); fclose(table); @@ -261,14 +260,13 @@ TEST(TestDataLog, VerifyMultipleTables) { // Verify table 4 { - FILE* table = fopen("table4.txt", "r"); + FILE* table = fopen("table_4.txt", "r"); ASSERT_FALSE(table == NULL); ExpectedValuesMap expected; expected["size,"] = ExpectedValues( std::vector(string_size, string_size + - sizeof(string_size) - / sizeof(std::string)), + kNumberOfRows), 1); ASSERT_EQ(DataLogParser::VerifyTable(table, expected), 0); fclose(table);