blob: 00539e4976ad7c427f0b24ff3211c9dde85ed7ea [file] [log] [blame]
#include "tlbmc/hal/shared_mem/client.h"
#include <cstdint>
#include <memory>
#include <string>
#include <utility>
#include "absl/base/no_destructor.h"
#include "absl/log/log.h"
#include "absl/status/status.h"
#include "absl/synchronization/mutex.h"
#include "tlbmc/hal/shared_mem/segment_manager.h"
#include "tlbmc/hal/shared_mem/sensors.h"
namespace milotic_tlbmc {
IpcClient& SharedMemoryClient::GetInstance() { return GetInstance(""); }
void SharedMemoryClient::SetUpInstanceForUnitTest() {
GetInstance("/tmp/tlbmc/tlbmc_shared_memory");
}
IpcClient& SharedMemoryClient::GetInstance(
const std::string& initialized_file_path) {
static absl::NoDestructor<SharedMemoryClient> instance(
Token(), initialized_file_path,
initialized_file_path.empty()
? SegmentManager::Get()
: SegmentManager::Get(initialized_file_path));
return *instance;
}
SharedMemoryClient::SharedMemoryClient(
Token token, const std::string& initialized_file_path,
std::unique_ptr<SegmentManager> segment_manager)
: initialized_file_path_(std::string{initialized_file_path}),
segment_manager_(std::move(segment_manager)) {}
SharedMemoryClient::SharedMemoryClient(
const std::string& initialized_file_path,
std::unique_ptr<SegmentManager> segment_manager)
: SharedMemoryClient(Token(), initialized_file_path,
std::move(segment_manager)) {}
SegmentManager* SharedMemoryClient::GetSegmentManager() {
absl::MutexLock lock(&segment_manager_mutex_);
if (segment_manager_ == nullptr) {
segment_manager_ = initialized_file_path_.empty()
? SegmentManager::Get()
: SegmentManager::Get(initialized_file_path_);
}
return segment_manager_.get();
}
void SharedMemoryClient::SetSegmentManager(
std::unique_ptr<SegmentManager> segment_manager) {
absl::MutexLock lock(&segment_manager_mutex_);
segment_manager_ = std::move(segment_manager);
}
IpcSensor* SharedMemoryClient::GetSensor(const std::string& sensor_name) {
absl::MutexLock lock(&sensors_mutex_);
auto it = sensors_.find(sensor_name);
if (it != sensors_.end()) {
return it->second;
}
SegmentManager* segment_manager = GetSegmentManager();
if (segment_manager == nullptr) {
return nullptr;
}
DLOG(INFO) << "SharedMemoryClient segment_manager: " << segment_manager;
IpcSensor* sensor = segment_manager->GetOrCreateSensor(sensor_name.c_str());
DLOG(INFO) << "SharedMemoryClient sensor for " << sensor_name << ": "
<< sensor;
sensors_[sensor_name] = sensor;
return sensor;
}
absl::Status SharedMemoryClient::UpdateSensorValue(
const std::string& sensor_name, float value) {
IpcSensor* sensor = GetSensor(sensor_name);
if (sensor == nullptr) {
if (GetSegmentManager() == nullptr) {
return absl::UnavailableError(
"Failed to get segment manager; this normally means the shared "
"memory is not initialized. Just wait for the initialization.");
}
return absl::InternalError(
"Failed to get sensor. This normally should not happen.");
}
sensor->SetValue(value);
return absl::OkStatus();
}
absl::Status SharedMemoryClient::UpdateSensorValue(
const std::string& sensor_name, float value, uint64_t timestamp) {
IpcSensor* sensor = GetSensor(sensor_name);
if (sensor == nullptr) {
if (GetSegmentManager() == nullptr) {
return absl::UnavailableError(
"Failed to get segment manager; this normally means the shared "
"memory is not initialized. Just wait for the initialization.");
}
return absl::InternalError(
"Failed to get sensor. This normally should not happen.");
}
sensor->SetValue(value, timestamp);
return absl::OkStatus();
}
} // namespace milotic_tlbmc