Skip to content

Commit 0e861f9

Browse files
TimoSteuerwaldETASFScholPer
authored andcommitted
Impl & unit test to print string in IdentifierHash
1 parent c8b48ee commit 0e861f9

11 files changed

Lines changed: 233 additions & 66 deletions

File tree

examples/control_application/control_daemon.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ int main(int argc, char** argv) {
4040
}
4141

4242
score::lcm::ControlClient client([](const score::lcm::ExecutionErrorEvent& event) {
43-
std::cerr << "Undefined state callback invoked for process group id: " << event.processGroup.data() << std::endl;
43+
std::cerr << "Undefined state callback invoked for process group id: " << event.processGroup << std::endl;
4444
});
4545

4646
score::safecpp::Scope<> scope{};

src/launch_manager_daemon/BUILD

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@
1212
# *******************************************************************************
1313
load("//config:common_cc.bzl", "cc_binary_with_common_opts", "cc_library_with_common_opts")
1414

15+
package(default_visibility = ["//tests:__subpackages__"])
16+
1517
cc_library(
1618
name = "config",
1719
hdrs = ["config/lm_flatcfg_generated.h"],

src/launch_manager_daemon/common/include/score/lcm/identifier_hash.hpp

Lines changed: 48 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -11,18 +11,21 @@
1111
* SPDX-License-Identifier: Apache-2.0
1212
********************************************************************************/
1313

14-
1514
#ifndef IDENTIFIER_HASH_H_
1615
#define IDENTIFIER_HASH_H_
1716

1817
#include <cstddef>
19-
18+
#include <optional>
19+
#include <ostream>
2020
#include <string>
2121
#include <string_view>
22+
#include <unordered_map>
2223

23-
namespace score {
24+
namespace score
25+
{
2426

25-
namespace lcm {
27+
namespace lcm
28+
{
2629

2730
/// @file identifier_hash.hpp
2831
/// @brief This file contains the declaration of the IdentifierHash class,
@@ -36,8 +39,9 @@ namespace lcm {
3639
/// @details The class is designed to be used in contexts where IDs needs to be managed,
3740
/// compared, and manipulated. It ensures that IDs are handled efficiently and provides
3841
/// necessary operators and functions for common operations.
39-
class IdentifierHash final {
40-
public:
42+
class IdentifierHash final
43+
{
44+
public:
4145
/// @brief Constructs an IdentifierHash object from the given ID.
4246
/// @param id A const reference to std::string representing an ID.
4347
explicit IdentifierHash(const std::string& id);
@@ -85,8 +89,8 @@ class IdentifierHash final {
8589
bool operator<(const IdentifierHash& other) const; // Overloaded operator for comparison
8690

8791
///@brief Default constructor for the IdentifierHash class.
88-
///This constructor initializes the IdentifierHash object with a default ID value.
89-
///The ID value is calculated by hashing an empty string using std::hash<std::string>.
92+
/// This constructor initializes the IdentifierHash object with a default ID value.
93+
/// The ID value is calculated by hashing an empty string using std::hash<std::string>.
9094

9195
// this constructor is used in the code that is not part of the POC
9296
// not sure if we should have this constructor or not, but there is code like this:
@@ -116,11 +120,46 @@ class IdentifierHash final {
116120
/// @return A constant reference to the data stored in the IdentifierHash object.
117121
std::size_t data() const;
118122

119-
private:
123+
/// @brief Returns the registry mapping hash values to their corresponding string representations.
124+
///
125+
/// Static registry, which gets initialized per process.
126+
///
127+
/// @return A reference to the static unordered_map that serves as the registry.
128+
static std::unordered_map<std::size_t, std::string>& get_registry();
129+
130+
private:
120131
/// internal representation of the ID, that was passed in constructor
121132
std::size_t hash_id_ = 0;
122133
};
123134

135+
/// @brief Overloaded stream insertion operator for IdentifierHash.
136+
///
137+
/// This operator allows IdentifierHash objects to be output to an ostream.
138+
/// It uses the the static registry to find the string representation of the hash ID.
139+
///
140+
/// If there is no value stored in the registry for the given hash
141+
/// (i.e. the IdentifierHash is not constructed in this process,
142+
/// instead it has been transferred from another process via e.g. shared memory),
143+
/// it outputs an error message.
144+
///
145+
/// @param os The output stream.
146+
/// @param id The IdentifierHash object to output.
147+
/// @return A reference to the output stream.
148+
inline std::ostream& operator<<(std::ostream& os, const IdentifierHash& id)
149+
{
150+
const auto& reg = IdentifierHash::get_registry();
151+
const auto it = reg.find(id.data());
152+
if (it != reg.end())
153+
{
154+
os << it->second;
155+
}
156+
else
157+
{
158+
os << "<Unknown IdentifierHash: " << id.data() << ">";
159+
}
160+
return os;
161+
}
162+
124163
} // namespace lcm
125164

126165
} // namespace score

src/launch_manager_daemon/common/src/identifier_hash.cpp

Lines changed: 38 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,13 @@
1313

1414
#include <score/lcm/identifier_hash.hpp>
1515
#include <functional>
16+
#include <unordered_map>
1617

17-
namespace score {
18+
namespace score
19+
{
1820

19-
namespace lcm {
21+
namespace lcm
22+
{
2023

2124
// Please note that a lot of the following info, would normally belong to identifier_hash.hpp file.
2225
// However, decision was made to publish identifier_hash.hpp alongside other headers.
@@ -55,47 +58,68 @@ namespace lcm {
5558
// One thing to note: hashing function is implementation specific.
5659
// So if this should work between different compilers, we may need to go for our own hash function.
5760

58-
IdentifierHash::IdentifierHash(const std::string& id) {
61+
IdentifierHash::IdentifierHash(const std::string& id)
62+
{
5963
hash_id_ = std::hash<std::string>{}(id);
64+
get_registry()[hash_id_] = id;
6065
}
6166

62-
IdentifierHash::IdentifierHash(std::string_view id) {
67+
IdentifierHash::IdentifierHash(std::string_view id)
68+
{
6369
hash_id_ = std::hash<std::string_view>{}(id);
70+
get_registry()[hash_id_] = id;
6471
}
6572

66-
IdentifierHash::IdentifierHash(const char* id) {
67-
hash_id_ =
68-
std::hash<std::string_view>{}(id != nullptr ? std::string_view(id) : std::string_view(""));
73+
IdentifierHash::IdentifierHash(const char* id)
74+
{
75+
const std::string_view sv = (id != nullptr) ? std::string_view(id) : std::string_view("");
76+
hash_id_ = std::hash<std::string_view>{}(sv);
77+
get_registry()[hash_id_] = sv;
6978
}
7079

71-
bool IdentifierHash::operator==(const IdentifierHash& other) const {
80+
bool IdentifierHash::operator==(const IdentifierHash& other) const
81+
{
7282
return hash_id_ == other.hash_id_;
7383
}
7484

75-
bool IdentifierHash::operator!=(const IdentifierHash& other) const {
85+
bool IdentifierHash::operator!=(const IdentifierHash& other) const
86+
{
7687
return !operator==(other);
7788
}
7889

79-
bool IdentifierHash::operator==(const std::string_view& other) const {
90+
bool IdentifierHash::operator==(const std::string_view& other) const
91+
{
8092
return hash_id_ == (IdentifierHash{other}).hash_id_;
8193
}
8294

83-
bool IdentifierHash::operator!=(const std::string_view& other) const {
95+
bool IdentifierHash::operator!=(const std::string_view& other) const
96+
{
8497
return !operator==(IdentifierHash{other});
8598
}
8699

87-
bool IdentifierHash::operator<(const IdentifierHash& other) const {
100+
bool IdentifierHash::operator<(const IdentifierHash& other) const
101+
{
88102
return hash_id_ < other.hash_id_;
89103
}
90104

91-
IdentifierHash::IdentifierHash() {
105+
IdentifierHash::IdentifierHash()
106+
{
92107
hash_id_ = std::hash<std::string_view>{}(std::string_view(""));
108+
get_registry()[hash_id_] = "";
93109
}
94110

95-
std::size_t IdentifierHash::data() const {
111+
std::size_t IdentifierHash::data() const
112+
{
96113
return hash_id_;
97114
}
98115

116+
std::unordered_map<std::size_t, std::string>& IdentifierHash::get_registry()
117+
{
118+
/// Static registry, which gets initialized per process.
119+
static std::unordered_map<std::size_t, std::string> registry;
120+
return registry;
121+
}
122+
99123
} // namespace lcm
100124

101125
} // namespace score

src/launch_manager_daemon/health_monitor_lib/src/score/lcm/saf/ifexm/ProcessStateReader.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -79,8 +79,8 @@ bool ProcessStateReader::distributeChanges(const timers::NanoSecondType f_syncTi
7979
const auto changedPosixProcess{resultChangedProcess.value()};
8080
if (changedPosixProcess)
8181
{
82-
logger_r.LogDebug() << "Process with Id" << changedPosixProcess->id.data() << "changed state PG"
83-
<< changedPosixProcess->processGroupStateId.data() << "PS"
82+
logger_r.LogDebug() << "Process with Id" << changedPosixProcess->id << "changed state PG"
83+
<< changedPosixProcess->processGroupStateId << "PS"
8484
<< static_cast<int>(changedPosixProcess->processStateId);
8585
isPushPending = pushUpdateTill(*changedPosixProcess, f_syncTimestamp);
8686
flagContinue = (!isPushPending);

src/launch_manager_daemon/src/configuration_manager/configurationmanager.cpp

Lines changed: 19 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -126,10 +126,10 @@ std::optional<const ProcessGroupStateID*> ConfigurationManager::getMainPGStartup
126126
if (pg_state) {
127127
result = &main_pg_startup_state_;
128128
} else {
129-
LM_LOG_DEBUG() << "Process group state not found:" << main_pg_startup_state_.pg_state_name_.data();
129+
LM_LOG_DEBUG() << "Process group state not found:" << main_pg_startup_state_.pg_state_name_;
130130
}
131131
} else {
132-
LM_LOG_DEBUG() << "Process group not found:" << main_pg_startup_state_.pg_name_.data();
132+
LM_LOG_DEBUG() << "Process group not found:" << main_pg_startup_state_.pg_name_;
133133
}
134134

135135
return result;
@@ -154,8 +154,8 @@ std::optional<const std::vector<uint32_t>*> ConfigurationManager::getProcessInde
154154
if (state) {
155155
result = &state->process_indexes_;
156156
} else {
157-
LM_LOG_DEBUG() << "Process group state '" << pg_state_id.pg_state_name_.data() << "' not found in group '"
158-
<< pg_state_id.pg_name_.data() << "'.";
157+
LM_LOG_DEBUG() << "Process group state '" << pg_state_id.pg_state_name_ << "' not found in group '"
158+
<< pg_state_id.pg_name_ << "'.";
159159
}
160160

161161
return result;
@@ -168,7 +168,7 @@ std::optional<const OsProcess*> ConfigurationManager::getOsProcessConfiguration(
168168
if (auto pg = getProcessGroupByNameAndIndex(pg_name, index)) {
169169
result = &(*pg)->processes_[index];
170170
} else {
171-
LM_LOG_DEBUG() << "Unable to retrieve process configuration for process group" << pg_name.data()
171+
LM_LOG_DEBUG() << "Unable to retrieve process configuration for process group" << pg_name
172172
<< "with index" << index;
173173
}
174174

@@ -182,7 +182,7 @@ std::optional<const DependencyList*> ConfigurationManager::getOsProcessDependenc
182182
if (auto pg = getProcessGroupByNameAndIndex(pg_name, index)) {
183183
result = &(*pg)->processes_[index].dependencies_;
184184
} else {
185-
LM_LOG_DEBUG() << "Unable to retrieve process dependencies for process group" << pg_name.data() << "with index"
185+
LM_LOG_DEBUG() << "Unable to retrieve process dependencies for process group" << pg_name << "with index"
186186
<< index;
187187
}
188188

@@ -304,7 +304,7 @@ bool ConfigurationManager::parseMachineConfigurations(const ModeGroup* node, con
304304
process_group_data.name_ = getStringViewFromFlatBuffer(node->identifier());
305305
process_group_data.sw_cluster_ = cluster;
306306
LM_LOG_DEBUG() << "FlatBufferParser::getModeGroupPgName:" << getStringFromFlatBuffer(node->identifier())
307-
<< "( IdentifierHash:" << process_group_data.name_.data() << ")";
307+
<< "( IdentifierHash:" << process_group_data.name_ << ")";
308308

309309
if (process_group_data.name_ != score::lcm::IdentifierHash(std::string_view(""))) {
310310
// Add process group name to the PG name list
@@ -339,7 +339,7 @@ bool ConfigurationManager::parseModeGroups(const ModeGroup* node, ProcessGroup&
339339
pg_state.name_ = getStringViewFromFlatBuffer(flatbuffer_string);
340340
LM_LOG_DEBUG() << "FlatBufferParser::getModeGroupPgStateName:"
341341
<< mode_declaration_node->identifier()->c_str()
342-
<< "( IdentifierHash:" << pg_state.name_.data() << ")";
342+
<< "( IdentifierHash:" << pg_state.name_ << ")";
343343
process_group_data.states_.push_back(pg_state);
344344
// Is this the "Off" state, i.e. does it end with "/Off" ?
345345
auto str_len = string_name.length();
@@ -593,8 +593,8 @@ void ConfigurationManager::parseProcessGroup(
593593
ProcessGroupStateID pg_info;
594594
pg_info.pg_name_ = getStringViewFromFlatBuffer(process_pg_node->stateMachine_name());
595595
pg_info.pg_state_name_ = getStringViewFromFlatBuffer(process_pg_node->stateName());
596-
LM_LOG_DEBUG() << "ParseProcessProcessGroup: id:::pg_name_:" << pg_info.pg_name_.data()
597-
<< ", pg_state_name_:" << pg_info.pg_state_name_.data();
596+
LM_LOG_DEBUG() << "ParseProcessProcessGroup: id:::pg_name_:" << pg_info.pg_name_
597+
<< ", pg_state_name_:" << pg_info.pg_state_name_;
598598

599599
// Assign OsProcess instance to the process group
600600
AssignOsProcessInstanceToProcessGroup(pg_info, process_instance);
@@ -618,7 +618,7 @@ void ConfigurationManager::parseExecutionDependency(
618618
dep.target_process_id_ = getStringViewFromFlatBuffer(process_dependency_node->targetProcess_identifier());
619619
LM_LOG_DEBUG() << "ParseProcessExecutionDependency: target process path:"
620620
<< getStringFromFlatBuffer(process_dependency_node->targetProcess_identifier())
621-
<< "ID:" << dep.target_process_id_.data();
621+
<< "ID:" << dep.target_process_id_;
622622
process_instance.dependencies_.push_back(dep);
623623

624624
}
@@ -715,10 +715,10 @@ void ConfigurationManager::AssignOsProcessInstanceToProcessGroup(const ProcessGr
715715
state->process_indexes_.push_back(index_in_pg);
716716
}
717717
} else {
718-
LM_LOG_WARN() << "Process group state not found:" << process_pg.pg_state_name_.data();
718+
LM_LOG_WARN() << "Process group state not found:" << process_pg.pg_state_name_;
719719
}
720720
} else {
721-
LM_LOG_WARN() << "Process group not found:", process_pg.pg_name_.data();
721+
LM_LOG_WARN() << "Process group not found:" << process_pg.pg_name_;
722722
}
723723
}
724724

@@ -827,10 +827,10 @@ osal::CommsType ConfigurationManager::isReportingProcess(const ExecutionStateRep
827827

828828
if (reporting_behaviour == ExecutionStateReportingBehaviorEnum::ExecutionStateReportingBehaviorEnum_ReportsExecutionState) {
829829
reporting_status = osal::CommsType::kReporting;
830-
LM_LOG_DEBUG() << "Process" << process_name.data() << "is Reporting execution state";
830+
LM_LOG_DEBUG() << "Process" << process_name << "is Reporting execution state";
831831
} else {
832832
// ExecutionStateReportingBehaviorEnum::DoesNotReportExecutionState
833-
LM_LOG_DEBUG() << "Process" << process_name.data() << "is NOT Reporting execution state";
833+
LM_LOG_DEBUG() << "Process" << process_name << "is NOT Reporting execution state";
834834
}
835835

836836
return reporting_status;
@@ -842,10 +842,10 @@ bool ConfigurationManager::isSelfTerminatingProcess(const TerminationBehaviorEnu
842842

843843
if (termination_behavior == TerminationBehaviorEnum::TerminationBehaviorEnum_ProcessIsSelfTerminating) {
844844
termination_status = true;
845-
LM_LOG_DEBUG() << "Process" << process_name.data() << "is Self terminating";
845+
LM_LOG_DEBUG() << "Process" << process_name << "is Self terminating";
846846
} else {
847847
// TerminationBehaviorEnum::ProcessIsNotSelfTerminating
848-
LM_LOG_DEBUG() << "Process" << process_name.data() << "is NOT Self terminating";
848+
LM_LOG_DEBUG() << "Process" << process_name << "is NOT Self terminating";
849849
}
850850

851851
return termination_status;
@@ -861,10 +861,10 @@ std::optional<const ProcessGroup*> ConfigurationManager::getProcessGroupByNameAn
861861
if (index < pg->processes_.size()) {
862862
result = pg;
863863
} else {
864-
LM_LOG_DEBUG() << "Process index" << index << "is out of bounds in process group" << pg_name.data();
864+
LM_LOG_DEBUG() << "Process index" << index << "is out of bounds in process group" << pg_name;
865865
}
866866
} else {
867-
LM_LOG_DEBUG() << "Process group not found:" << pg_name.data();
867+
LM_LOG_DEBUG() << "Process group not found:" << pg_name;
868868
}
869869

870870
return result;

0 commit comments

Comments
 (0)