Skip to content
Merged

Dev #184

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .codespellrc
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,6 @@
builtin = clear,rare,en-GB_to_en-US,names,informal,code
check-filenames =
check-hidden =
ignore-words-list = weill,sinc,mut,numer,uint,stdio,ws
skip = */.git,*/build,*/prefix,./scripts/all_plugins,./libs
ignore-words-list = weill,sinc,mut,numer,uint,stdio,ws,indx
skip = */.git,*/build,*/prefix,./scripts/all_plugins,./libs,.venv
quiet-level = 2
2 changes: 1 addition & 1 deletion docs/Doxyfile
Original file line number Diff line number Diff line change
Expand Up @@ -559,7 +559,7 @@ INTERNAL_DOCS = NO
# names in lower-case letters. If set to YES, upper-case letters are also
# allowed. This is useful if you have classes or files whose names only differ
# in case and if your file system supports case sensitive file names. Windows
# (including Cygwin) ands Mac users are advised to set this option to NO.
# (including Cygwin) and Mac users are advised to set this option to NO.
# The default value is: system dependent.

CASE_SENSE_NAMES = NO
Expand Down
2 changes: 1 addition & 1 deletion docs/Doxyfile.in
Original file line number Diff line number Diff line change
Expand Up @@ -559,7 +559,7 @@ INTERNAL_DOCS = NO
# names in lower-case letters. If set to YES, upper-case letters are also
# allowed. This is useful if you have classes or files whose names only differ
# in case and if your file system supports case sensitive file names. Windows
# (including Cygwin) ands Mac users are advised to set this option to NO.
# (including Cygwin) and Mac users are advised to set this option to NO.
# The default value is: system dependent.

CASE_SENSE_NAMES = NO
Expand Down
22 changes: 11 additions & 11 deletions src/io.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,52 +35,52 @@ IO::Block::Block(std::string blockname,
port.value = 0.0;
port.buff_value = 0.0;
// NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-constant-array-index)
ports[channel.flags].push_back(port);
ports.at(channel.flags).push_back(port);
port = {};
}
}

size_t IO::Block::getCount(IO::flags_t type) const
{
// NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-constant-array-index)
return this->ports[type].size();
return this->ports.at(type).size();
}

std::string IO::Block::getChannelName(IO::flags_t type, size_t index) const
{
// NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-constant-array-index)
return this->ports[type][index].channel_info.name;
return this->ports.at(type).at(index).channel_info.name;
}

std::string IO::Block::getChannelDescription(IO::flags_t type,
size_t index) const
{
// NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-constant-array-index)
return this->ports[type][index].channel_info.description;
return this->ports.at(type).at(index).channel_info.description;
}

void IO::Block::writeinput(size_t index, const double& data)
{
this->ports[IO::INPUT][index].buff_value += data;
this->ports.at(IO::INPUT).at(index).buff_value += data;
}

double& IO::Block::readinput(size_t index)
{
// We must reset input values to zero so that the next cycle doesn't use these
// values
this->ports[IO::INPUT][index].value =
this->ports[IO::INPUT][index].buff_value;
this->ports[IO::INPUT][index].buff_value = 0.0;
return this->ports[IO::INPUT][index].value;
this->ports.at(IO::INPUT).at(index).value =
this->ports.at(IO::INPUT).at(index).buff_value;
this->ports.at(IO::INPUT).at(index).buff_value = 0.0;
return this->ports.at(IO::INPUT).at(index).value;
}

void IO::Block::writeoutput(size_t index, const double& data)
{
this->ports[IO::OUTPUT][index].value = data;
this->ports.at(IO::OUTPUT).at(index).value = data;
}

const double& IO::Block::readPort(IO::flags_t direction, size_t index)
{
return this->ports[direction][index].value;
return this->ports.at(direction).at(index).value;
}
// NOLINTEND(cppcoreguidelines-pro-bounds-constant-array-index)
53 changes: 33 additions & 20 deletions src/main_window.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,11 @@
// deserialize it back when loading settings.
struct plugin_connection
{
quint64 src_id;
quint64 src_direction;
quint64 src_port;
quint64 dest_id;
quint64 dest_port;
qint32 src_id;
qint32 src_direction;
qint32 src_port;
qint32 dest_id;
qint32 dest_port;
};

QDataStream& operator<<(QDataStream& out, const plugin_connection& conn)
Expand Down Expand Up @@ -534,7 +534,7 @@ void MainWindow::saveDAQSettings(QSettings& userprefs)
}

void MainWindow::loadDAQSettings(
QSettings& userprefs, std::unordered_map<size_t, IO::Block*> block_cache)
QSettings& userprefs, std::unordered_map<int, IO::Block*>& block_cache)
{
userprefs.beginGroup("DAQs");
Event::Object get_devices_event(Event::Type::DAQ_DEVICE_QUERY_EVENT);
Expand Down Expand Up @@ -652,7 +652,7 @@ void MainWindow::loadDAQSettings(
}
userprefs.endGroup(); // Digital Output
userprefs.endGroup(); // Device name
block_cache[device_id.toUInt()] = tmp_device;
block_cache[device_id.toInt()] = tmp_device;
}
userprefs.endGroup(); // DAQ
}
Expand All @@ -664,9 +664,18 @@ void MainWindow::saveWidgetSettings(QSettings& userprefs)
this->event_manager->postEvent(&loaded_plugins_query);
const auto plugin_list = std::any_cast<std::vector<const Widgets::Plugin*>>(
loaded_plugins_query.getParam("plugins"));
int widget_count = 0;
int non_component_plugin_id = -1;
int plugin_id = 0;
for (const auto& entry : plugin_list) {
userprefs.beginGroup(QString::number(widget_count++));
// We don't expect the number of blocks in the system to exceed the max
// positive value of int In 2025 you would run out of memory first before
// that happens. Additionally we are saving negative values to indicate to
// the workspace loading system that the negative valued plugins do not
// contain a component and therefore should be left out of the connection
// loading step.
plugin_id = entry->hasComponent() ? static_cast<int>(entry->getID())
: non_component_plugin_id--;
userprefs.beginGroup(QString::number(plugin_id));
userprefs.setValue("library", QString::fromStdString(entry->getLibrary()));
userprefs.beginGroup("standardParams");
entry->saveParameterSettings(userprefs);
Expand All @@ -680,7 +689,7 @@ void MainWindow::saveWidgetSettings(QSettings& userprefs)
}

void MainWindow::loadWidgetSettings(
QSettings& userprefs, std::unordered_map<size_t, IO::Block*> block_cache)
QSettings& userprefs, std::unordered_map<int, IO::Block*>& block_cache)
{
userprefs.beginGroup("Widgets");
QString plugin_name;
Expand All @@ -698,7 +707,7 @@ void MainWindow::loadWidgetSettings(
plugin_ptr->loadCustomParameterSettings(userprefs);
userprefs.endGroup(); // customParams
userprefs.endGroup(); // plugin_instance_id
block_cache[plugin_instance_id.toUInt()] = plugin_ptr->getBlock();
block_cache[plugin_instance_id.toInt()] = plugin_ptr->getBlock();
}
userprefs.endGroup(); // Widgets
}
Expand All @@ -722,19 +731,21 @@ void MainWindow::saveConnectionSettings(QSettings& userprefs)
{
continue;
}
id_connection.src_id = conn.src->getID();
id_connection.src_direction = conn.src_port_type;
id_connection.src_port = conn.src_port;
id_connection.dest_id = conn.dest->getID();
id_connection.dest_port = conn.dest_port;
// We need to match the block id with the id already stored in the
// settings file when saveWidgets was called.
id_connection.src_id = static_cast<int>(conn.src->getID());
id_connection.src_direction = static_cast<int>(conn.src_port_type);
id_connection.src_port = static_cast<int>(conn.src_port);
id_connection.dest_id = static_cast<int>(conn.dest->getID());
id_connection.dest_port = static_cast<int>(conn.dest_port);
userprefs.setValue(QString::number(connection_count++),
QVariant::fromValue(id_connection));
}
userprefs.endGroup(); // Connections
}

void MainWindow::loadConnectionSettings(
QSettings& userprefs, std::unordered_map<size_t, IO::Block*> block_cache)
QSettings& userprefs, std::unordered_map<int, IO::Block*>& block_cache)
{
///////////////////// Load connections /////////////////////////
RT::block_connection_t connection;
Expand All @@ -754,9 +765,9 @@ void MainWindow::loadConnectionSettings(
connection.src = block_cache[id_connection.src_id];
connection.src_port_type =
static_cast<IO::flags_t>(id_connection.src_direction);
connection.src_port = id_connection.src_port;
connection.src_port = static_cast<size_t>(id_connection.src_port);
connection.dest = block_cache[id_connection.dest_id];
connection.dest_port = id_connection.dest_port;
connection.dest_port = static_cast<size_t>(id_connection.dest_port);
connection_events.emplace_back(Event::Type::IO_LINK_INSERT_EVENT);
connection_events.back().setParam("connection", std::any(connection));
}
Expand Down Expand Up @@ -785,7 +796,7 @@ void MainWindow::loadSettings()
mdiArea->closeAllSubWindows();
const auto workspace_filename = userprefs.value(profile).toString();
QSettings workspaceprefs(workspace_filename, QSettings::IniFormat);
std::unordered_map<size_t, IO::Block*> blocks;
std::unordered_map<int, IO::Block*> blocks;
this->loadPeriodSettings(workspaceprefs);

this->loadDAQSettings(workspaceprefs, blocks);
Expand Down Expand Up @@ -837,6 +848,8 @@ void MainWindow::saveSettings()

this->saveWidgetSettings(workspaceprefs);

this->saveConnectionSettings(workspaceprefs);

userprefs.endGroup(); // Workspaces
}

Expand Down
9 changes: 5 additions & 4 deletions src/main_window.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@

#include <QDialog>
#include <QMainWindow>
#include <unordered_map>

#include "event.hpp"

Expand Down Expand Up @@ -177,14 +178,14 @@ private slots:
inline void savePeriodSettings(QSettings& userprefs);
inline void loadPeriodSettings(QSettings& userprefs);
inline void saveDAQSettings(QSettings& userprefs);
inline void loadDAQSettings(
QSettings& userprefs, std::unordered_map<size_t, IO::Block*> block_cache);
inline void loadDAQSettings(QSettings& userprefs,
std::unordered_map<int, IO::Block*>& block_cache);
inline void saveWidgetSettings(QSettings& userprefs);
inline void loadWidgetSettings(
QSettings& userprefs, std::unordered_map<size_t, IO::Block*> block_cache);
QSettings& userprefs, std::unordered_map<int, IO::Block*>& block_cache);
inline void saveConnectionSettings(QSettings& userprefs);
inline void loadConnectionSettings(
QSettings& userprefs, std::unordered_map<size_t, IO::Block*> block_cache);
QSettings& userprefs, std::unordered_map<int, IO::Block*>& block_cache);
Event::Manager* event_manager;
QMdiArea* mdiArea = nullptr;
QList<QMdiSubWindow*> subWindows;
Expand Down
54 changes: 41 additions & 13 deletions src/nidaq_driver.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -184,6 +184,27 @@ inline void printError(int32_t status)
ERROR_MSG("Message : {}", std::string(err_buff.data()));
}

inline void printExtendedError(int32_t status)
{
if (status == 0) {
return;
}
ERROR_MSG("NIDAQ ERROR : code {}", status);
const int32_t error_size = DAQmxGetExtendedErrorInfo(nullptr, 0);
if (error_size < 0) {
ERROR_MSG("Unable to get code message");
return;
}
std::vector<char> err_buff(static_cast<size_t>(error_size));
const int32_t errcode = DAQmxGetExtendedErrorInfo(
err_buff.data(), static_cast<uint32_t>(error_size));
if (errcode < 0) {
ERROR_MSG("Unable to parse message");
return;
}
ERROR_MSG("Message : {}", std::string(err_buff.data()));
}

inline std::string physical_card_name(const std::string& device_name)
{
std::array<char, 1024> buffer {};
Expand Down Expand Up @@ -218,6 +239,8 @@ struct physical_channel_t
int32_t physical_channel_t::addToTask(TaskHandle task_handle) const
{
int32_t err = 0;
int32_t shunt_resistance_location = 0;
int32_t shunt_resisntance_value = 0;
const std::string units = DAQ::get_default_units().at(units_index);
auto [min, max] = DAQ::get_default_ranges().at(range_index);
switch (type) {
Expand All @@ -232,20 +255,22 @@ int32_t physical_channel_t::addToTask(TaskHandle task_handle) const
DAQmx_Val_Volts,
nullptr);
} else if (units == "amps") {
DAQmxGetAICurrentShuntLoc(
task_handle, name.c_str(), &shunt_resistance_location);
err = DAQmxCreateAICurrentChan(task_handle,
name.c_str(),
nullptr,
reference,
min,
max,
DAQmx_Val_Diff,
min / 1000.0,
max / 1000.0,
DAQmx_Val_Amps,
DAQmx_Val_Default,
0,
shunt_resistance_location,
249.0,
nullptr);
} else {
ERROR_MSG("NIDAQ : Virtual Channel Creation : Unknown units {}", units);
}
printError(err);
printExtendedError(err);
break;
case DAQ::ChannelType::AO:
if (units == "volts") {
Expand All @@ -267,17 +292,17 @@ int32_t physical_channel_t::addToTask(TaskHandle task_handle) const
} else {
ERROR_MSG("NIDAQ : Virtual Channel Creation : Unknown units {}", units);
}
printError(err);
printExtendedError(err);
break;
case DAQ::ChannelType::DI:
err = DAQmxCreateDIChan(
task_handle, name.c_str(), nullptr, DAQmx_Val_ChanPerLine);
printError(err);
printExtendedError(err);
break;
case DAQ::ChannelType::DO:
err = DAQmxCreateDOChan(
task_handle, name.c_str(), nullptr, DAQmx_Val_ChanPerLine);
printError(err);
printExtendedError(err);
break;
default:
ERROR_MSG("NIDAQ_DRIVER : Channel Type Unknown");
Expand Down Expand Up @@ -516,7 +541,7 @@ int Device::setChannelActive(DAQ::ChannelType::type_t type,
DAQmxClearTask(task);
err = DAQmxCreateTask(DAQ::ChannelType::type2string(type).c_str(), &task);
if (err != 0) {
printError(err);
printExtendedError(err);
for (auto& channel : physical_channels_registry.at(type)) {
channel.active = false;
}
Expand Down Expand Up @@ -554,9 +579,9 @@ int Device::setChannelActive(DAQ::ChannelType::type_t type,
}
}
if (DAQmxGetTaskChannels(task, nullptr, 0) > 0) {
printError(DAQmxSetSampTimingType(task, DAQmx_Val_OnDemand));
printError(DAQmxTaskControl(task, DAQmx_Val_Task_Commit));
printError(DAQmxStartTask(task));
printExtendedError(DAQmxSetSampTimingType(task, DAQmx_Val_OnDemand));
printExtendedError(DAQmxTaskControl(task, DAQmx_Val_Task_Commit));
printExtendedError(DAQmxStartTask(task));
}
return err;
}
Expand Down Expand Up @@ -993,6 +1018,9 @@ void Driver::loadDevices()
printError(device_names_buffer_size);
return;
}
if (device_names_buffer_size == 0) {
return;
}
const std::string alpha = "abcdefghijklmnopqrstuvwxyz";
std::vector<char> buffer(static_cast<size_t>(device_names_buffer_size));
DAQmxGetSysDevNames(buffer.data(), static_cast<uint32_t>(buffer.size()));
Expand Down
2 changes: 1 addition & 1 deletion src/rtos.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ int setPeriod(Task* task, int64_t period);
* real-time loop. Available inside execute().
*
* \returns Period of the realtime thread the calling function is
* runninng from, -1 otherwise.
* running from, -1 otherwise.
*
* \sa RT::OS::sleepTimestep
*/
Expand Down
2 changes: 1 addition & 1 deletion src/widgets.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -304,7 +304,7 @@ void Widgets::Panel::updatePauseButton()
return;
}
const bool paused = state == RT::State::PAUSE;
pauseButton->setChecked(paused);
pauseButton->setDown(paused);
}

void Widgets::Panel::update_state(RT::State::state_t flag)
Expand Down
1 change: 1 addition & 0 deletions src/widgets.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -719,6 +719,7 @@ class Plugin : public Event::Handler
* \return IO::Block pointer to the internal structure
*/
IO::Block* getBlock() { return plugin_component.get(); }
const IO::Block* getBlock() const { return plugin_component.get(); }

protected:
Widgets::Component* getComponent();
Expand Down
Loading