1
0
Fork 0

thread protect metadata with a mutex

This commit is contained in:
Kevin Matz 2023-04-06 08:33:57 -04:00
parent 024d965f83
commit fa2625f77d
2 changed files with 105 additions and 40 deletions

View File

@ -60,6 +60,7 @@ Widget::~Widget()
*/
void Widget::init()
{
std::scoped_lock lock(mtx_metadata_);
usb_mode_ = USBdevice;
}
@ -71,6 +72,7 @@ void Widget::init()
*/
void Widget::halt()
{
std::scoped_lock lock(mtx_metadata_);
usb_mode_ = USBunknown;
}
@ -82,6 +84,7 @@ void Widget::halt()
*/
void Widget::open()
{
std::scoped_lock lock(mtx_metadata_);
usb_mode_ = USBhost;
}
@ -93,6 +96,7 @@ void Widget::open()
*/
void Widget::close()
{
std::scoped_lock lock(mtx_metadata_);
usb_mode_ = USBunknown;
}
@ -103,7 +107,8 @@ void Widget::close()
void Widget::setModeController()
{
sendDmx();
data_changed_token_ = onDataChange([this](DMX::Universe*){sendDmx();});
std::scoped_lock lock(mtx_metadata_);
token_data_changed_ = onDataChange([this](DMX::Universe*){sendDmx();});
}
@ -113,14 +118,50 @@ void Widget::setModeController()
*/
void Widget::setModeBridge(Pro::DMX_RX_MODE mode)
{
data_changed_token_ = nullptr;
rx_update_mode_ = mode;
{
std::scoped_lock lock(mtx_metadata_);
token_data_changed_ = nullptr;
rx_update_mode_ = mode;
}
auto msg = std::make_shared<Pro::MsgRecieveDMXOnChange>();
msg->mode = mode;
sendMessage(msg);
}
/**
* @brief Widget::serialNumber
* @return
*/
uint32_t Widget::serialNumber() const
{
std::scoped_lock lock(mtx_metadata_);
return serial_number;
}
/**
* @brief Widget::firmwareVersion
* @return
*/
uint16_t Widget::firmwareVersion() const
{
std::scoped_lock lock(mtx_metadata_);
return firmware_version;
}
/**
* @brief Widget::txBreakTime
* @return
*/
double Widget::txBreakTime() const
{
std::scoped_lock lock(mtx_metadata_);
return tx_break_intervals * Pro::DMX_BREAK_INTERVAL;
}
/**
* @brief Widget::setTxBreakTime
* @param time
@ -139,10 +180,22 @@ void Widget::setTxBreakIntervals(uint8_t count)
{
count = std::max(count, Pro::DMX_BREAK_MIN);
count = std::min(count, Pro::DMX_BREAK_MAX);
std::scoped_lock lock(mtx_metadata_);
tx_break_intervals = count;
}
/**
* @brief txMabTime
* @return
*/
double Widget::txMabTime() const
{
std::scoped_lock lock(mtx_metadata_);
return tx_mab_intervals * Pro::DMX_MAB_INTERVAL;
}
/**
* @brief Widget::setTxMabTime
* @param time
@ -161,16 +214,29 @@ void Widget::setTxMabIntervals(uint8_t count)
{
count = std::max(count, Pro::DMX_MAB_MIN);
count = std::min(count, Pro::DMX_MAB_MAX);
std::scoped_lock lock(mtx_metadata_);
tx_mab_intervals = count;
}
/**
* @brief txRate
* @return
*/
uint8_t Widget::txRate() const
{
std::scoped_lock lock(mtx_metadata_);
return tx_rate;
}
/**
* @brief Widget::setTxRate
* @param rate
*/
void Widget::setTxRate(uint8_t rate)
{
std::scoped_lock lock(mtx_metadata_);
tx_rate = std::min(rate, Pro::DMX_RATE_MAX);
}
@ -347,10 +413,13 @@ void Widget::getParameters(size_t user_length)
void Widget::setParameters() const
{
auto msg = std::make_shared<Pro::MsgSetWidgetParametersRequest>();
msg->break_time = tx_break_intervals;
msg->mab_time = tx_mab_intervals;
msg->rate = tx_rate;
msg->user_data = user_configuration;
{
std::scoped_lock lock(mtx_metadata_);
msg->break_time = tx_break_intervals;
msg->mab_time = tx_mab_intervals;
msg->rate = tx_rate;
msg->user_data = user_configuration;
}
sendMessage(msg);
}
@ -366,7 +435,10 @@ void Widget::sendDmx(bool trimmed) const
uint16_t l = null_start_data.size() - 1;
if (trimmed)
for (l = null_start_data.size() - 1; l > 0 && null_start_data[l] == 0; --l) {};
std::copy(null_start_data.begin(), null_start_data.begin() + l + 1, msg->data.begin());
{
std::scoped_lock lock(mtx_data);
std::copy(null_start_data.begin(), null_start_data.begin() + l + 1, msg->data.begin());
}
sendMessage(msg);
}
@ -410,11 +482,13 @@ void Widget::rxMsgProgramFlashPageReply(std::shared_ptr<Pro::MsgProgramFlashPage
void Widget::rxMsgGetWidgetParametersRequest(std::shared_ptr<Pro::MsgGetWidgetParametersRequest> msg)
{
auto reply = std::make_shared<Pro::MsgGetWidgetParametersReply>();
reply->break_time = tx_break_intervals;
reply->mab_time = tx_mab_intervals;
reply->rate = tx_rate;
reply->user_data = std::vector<uint8_t>(user_configuration);
{
std::scoped_lock lock(mtx_metadata_);
reply->break_time = tx_break_intervals;
reply->mab_time = tx_mab_intervals;
reply->rate = tx_rate;
reply->user_data = std::vector<uint8_t>(user_configuration);
}
reply->user_data.resize(msg->size, 0);
sendMessage(reply);
@ -429,6 +503,7 @@ void Widget::rxMsgGetWidgetParametersRequest(std::shared_ptr<Pro::MsgGetWidgetPa
*/
void Widget::rxMsgGetWidgetParametersReply(std::shared_ptr<Pro::MsgGetWidgetParametersReply> msg)
{
std::scoped_lock lock(mtx_metadata_);
firmware_version = msg->version;
tx_break_intervals = msg->break_time;
tx_mab_intervals = msg->mab_time;
@ -443,6 +518,7 @@ void Widget::rxMsgGetWidgetParametersReply(std::shared_ptr<Pro::MsgGetWidgetPara
*/
void Widget::rxMsgSetWidgetParametersRequest(std::shared_ptr<Pro::MsgSetWidgetParametersRequest> msg)
{
std::scoped_lock lock(mtx_metadata_);
setTxBreakIntervals(msg->break_time);
setTxMabIntervals(msg->mab_time);
setTxRate(msg->rate);
@ -500,6 +576,7 @@ void Widget::rxMsgSendRDMData(std::shared_ptr<Pro::MsgSendRDMData> msg)
void Widget::rxMsgRecieveDMXOnChange(std::shared_ptr<Pro::MsgRecieveDMXOnChange> msg)
{
setData(std::vector<uint8_t>(DMX::E111_LAST_SLOT+1, 0)); // clear dimmer data
std::scoped_lock lock(mtx_metadata_);
rx_update_mode_ = msg->mode;
}
@ -521,7 +598,10 @@ void Widget::rxMsgRecievedDMXChanged(std::shared_ptr<Pro::MsgRecievedDMXChanged>
void Widget::rxMsgGetWidgetSerialRequest(std::shared_ptr<Pro::MsgGetWidgetSerialRequest>)
{
auto reply = std::make_shared<Pro::MsgGetWidgetSerialReply>();
reply->serial = serial_number;
{
std::scoped_lock lock(mtx_metadata_);
reply->serial = serial_number;
}
sendMessage(reply);
}
@ -532,6 +612,7 @@ void Widget::rxMsgGetWidgetSerialRequest(std::shared_ptr<Pro::MsgGetWidgetSerial
*/
void Widget::rxMsgGetWidgetSerialReply(std::shared_ptr<Pro::MsgGetWidgetSerialReply> msg)
{
std::scoped_lock lock(mtx_metadata_);
serial_number = msg->serial;
}

View File

@ -25,8 +25,9 @@
#include "pro.h"
#include <universe.h>
#include <cstring>
#include <mutex>
#include <universe.h>
#include <vector>
namespace ENTTEC {
@ -51,39 +52,21 @@ public:
virtual void setModeController();
virtual void setModeBridge(Pro::DMX_RX_MODE = Pro::RxNotifyAlways);
/**
* @brief serial
* @return
*/
uint32_t serialNumber() const { return serial_number; }
/**
* @brief firmware
* @return
*/
uint16_t firmwareVersion() const { return firmware_version; }
/**
* @brief txBreakTime
* @return
*/
double txBreakTime() const { return tx_break_intervals * Pro::DMX_BREAK_INTERVAL; }
uint32_t serialNumber() const;
uint16_t firmwareVersion() const;
double txBreakTime() const;
void setTxBreakTime(double);
void setTxBreakIntervals(uint8_t);
/**
* @brief txMabTime
* @return
*/
double txMabTime() const { return tx_mab_intervals * Pro::DMX_MAB_INTERVAL; }
double txMabTime() const;
void setTxMabTime(double);
void setTxMabIntervals(uint8_t);
/**
* @brief txRate
* @return
*/
uint8_t txRate() const { return tx_rate; }
uint8_t txRate() const;
void setTxRate(uint8_t);
protected:
void routeRxMessage(std::shared_ptr<Pro::MessageData>);
@ -134,6 +117,7 @@ private:
USBdevice
} usb_mode_;
mutable std::mutex mtx_metadata_;
std::shared_ptr<void> data_changed_token_;
};