Skip to content

Commit 1ab06e2

Browse files
authored
Merge pull request #505 from avinxshKD/fix/cpp-read-status-498
cpp: add read status result and params parse fix
2 parents 9b75ea0 + 04f86fa commit 1ab06e2

File tree

4 files changed

+175
-15
lines changed

4 files changed

+175
-15
lines changed

TestConcoreHpp.cpp

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,20 @@ static void test_read_FM_missing_file_uses_initstr() {
9797
check("missing_file fallback val==3.0", approx(v[0], 3.0));
9898
}
9999

100+
static void test_read_result_missing_file_status() {
101+
setup_dirs();
102+
rm("in1/no_port_status");
103+
104+
Concore c;
105+
c.delay = 0;
106+
c.simtime = 0.0;
107+
108+
Concore::ReadResult r = c.read_result(1, "no_port_status", "[9.0,3.0]");
109+
check("read_result missing status FILE_NOT_FOUND",
110+
r.status == Concore::ReadStatus::FILE_NOT_FOUND);
111+
check("read_result missing uses initstr", r.data.size() == 1 && approx(r.data[0], 3.0));
112+
}
113+
100114
// ------------- write_FM --------------------------------------------------
101115

102116
static void test_write_FM_creates_file() {
@@ -274,6 +288,20 @@ static void test_tryparam_missing_key_uses_default() {
274288
c.tryparam("no_key", "def_val") == "def_val");
275289
}
276290

291+
static void test_load_params_semicolon_format() {
292+
setup_dirs();
293+
write_file("in/1/concore.params", "a=1;b=2");
294+
295+
Concore c;
296+
c.delay = 0;
297+
c.load_params();
298+
299+
check("load_params semicolon parses a", c.tryparam("a", "") == "1");
300+
check("load_params semicolon parses b", c.tryparam("b", "") == "2");
301+
302+
rm("in/1/concore.params");
303+
}
304+
277305
// ------------- main -------------------------------------------------------
278306

279307
int main() {
@@ -282,6 +310,7 @@ int main() {
282310
// read_FM / write_FM
283311
test_read_FM_file();
284312
test_read_FM_missing_file_uses_initstr();
313+
test_read_result_missing_file_status();
285314
test_write_FM_creates_file();
286315

287316
// unchanged()
@@ -307,6 +336,7 @@ int main() {
307336
// tryparam()
308337
test_tryparam_found();
309338
test_tryparam_missing_key_uses_default();
339+
test_load_params_semicolon_format();
310340

311341
std::cout << "\n=== Results: " << passed << " passed, " << failed
312342
<< " failed out of " << (passed + failed) << " tests ===\n";

concore.hpp

Lines changed: 74 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -54,13 +54,27 @@ class Concore{
5454
#endif
5555

5656
public:
57+
enum class ReadStatus {
58+
SUCCESS,
59+
TIMEOUT,
60+
PARSE_ERROR,
61+
FILE_NOT_FOUND,
62+
RETRIES_EXCEEDED
63+
};
64+
65+
struct ReadResult {
66+
ReadStatus status;
67+
vector<double> data;
68+
};
69+
5770
double delay = 1;
5871
int retrycount = 0;
5972
double simtime;
6073
int maxtime = 100;
6174
map <string, int> iport;
6275
map <string, int> oport;
6376
map <string, string> params;
77+
ReadStatus last_read_status = ReadStatus::SUCCESS;
6478

6579
/**
6680
* @brief Constructor for Concore class.
@@ -372,6 +386,14 @@ class Concore{
372386
return read_FM(port, name, initstr);
373387
}
374388

389+
ReadResult read_result(int port, string name, string initstr)
390+
{
391+
ReadResult result;
392+
result.data = read(port, name, initstr);
393+
result.status = last_read_status;
394+
return result;
395+
}
396+
375397
/**
376398
* @brief Reads data from a specified port and name using the FM (File Method) communication protocol.
377399
* @param port The port number.
@@ -383,6 +405,7 @@ class Concore{
383405
chrono::milliseconds timespan((int)(1000*delay));
384406
this_thread::sleep_for(timespan);
385407
string ins;
408+
ReadStatus status = ReadStatus::SUCCESS;
386409
try {
387410
ifstream infile;
388411
infile.open(inpath+to_string(port)+"/"+name, ios::in);
@@ -393,10 +416,13 @@ class Concore{
393416
infile.close();
394417
}
395418
else {
419+
status = ReadStatus::FILE_NOT_FOUND;
396420
throw 505;}
397421
}
398422
catch (...) {
399423
ins = initstr;
424+
if (status == ReadStatus::SUCCESS)
425+
status = ReadStatus::FILE_NOT_FOUND;
400426
}
401427

402428
int retry = 0;
@@ -424,14 +450,24 @@ class Concore{
424450
}
425451
retry++;
426452
}
453+
if ((int)ins.length()==0)
454+
status = ReadStatus::RETRIES_EXCEEDED;
427455
s += ins;
428456

429457
vector<double> inval = parser(ins);
430-
if(inval.empty())
458+
if(inval.empty()) {
459+
if (status == ReadStatus::SUCCESS)
460+
status = ReadStatus::PARSE_ERROR;
431461
inval = parser(initstr);
432-
if(inval.empty())
462+
}
463+
if(inval.empty()) {
464+
if (status == ReadStatus::SUCCESS)
465+
status = ReadStatus::PARSE_ERROR;
466+
last_read_status = status;
433467
return inval;
468+
}
434469
simtime = simtime > inval[0] ? simtime : inval[0];
470+
last_read_status = status;
435471

436472
//returning a string with data excluding simtime
437473
inval.erase(inval.begin());
@@ -450,6 +486,7 @@ class Concore{
450486
chrono::milliseconds timespan((int)(1000*delay));
451487
this_thread::sleep_for(timespan);
452488
string ins = "";
489+
ReadStatus status = ReadStatus::SUCCESS;
453490
try {
454491
if (shmId_get != -1) {
455492
if (sharedData_get && sharedData_get[0] != '\0') {
@@ -463,10 +500,13 @@ class Concore{
463500
}
464501
else
465502
{
503+
status = ReadStatus::FILE_NOT_FOUND;
466504
throw 505;
467505
}
468506
} catch (...) {
469507
ins = initstr;
508+
if (status == ReadStatus::SUCCESS)
509+
status = ReadStatus::FILE_NOT_FOUND;
470510
}
471511

472512
int retry = 0;
@@ -490,14 +530,24 @@ class Concore{
490530
}
491531
retry++;
492532
}
533+
if ((int)ins.length()==0)
534+
status = ReadStatus::RETRIES_EXCEEDED;
493535
s += ins;
494536

495537
vector<double> inval = parser(ins);
496-
if(inval.empty())
538+
if(inval.empty()) {
539+
if (status == ReadStatus::SUCCESS)
540+
status = ReadStatus::PARSE_ERROR;
497541
inval = parser(initstr);
498-
if(inval.empty())
542+
}
543+
if(inval.empty()) {
544+
if (status == ReadStatus::SUCCESS)
545+
status = ReadStatus::PARSE_ERROR;
546+
last_read_status = status;
499547
return inval;
548+
}
500549
simtime = simtime > inval[0] ? simtime : inval[0];
550+
last_read_status = status;
501551

502552
//returning a string with data excluding simtime
503553
inval.erase(inval.begin());
@@ -674,15 +724,26 @@ class Concore{
674724
* @return a vector of double values
675725
*/
676726
vector<double> read_ZMQ(string port_name, string name, string initstr) {
727+
ReadStatus status = ReadStatus::SUCCESS;
677728
auto it = zmq_ports.find(port_name);
678729
if (it == zmq_ports.end()) {
679730
cerr << "read_ZMQ: port '" << port_name << "' not initialized" << endl;
731+
status = ReadStatus::FILE_NOT_FOUND;
732+
last_read_status = status;
680733
return parser(initstr);
681734
}
682735
vector<double> inval = it->second->recv_with_retry();
683-
if (inval.empty())
736+
if (inval.empty()) {
737+
status = ReadStatus::TIMEOUT;
684738
inval = parser(initstr);
685-
if (inval.empty()) return inval;
739+
}
740+
if (inval.empty()) {
741+
if (status == ReadStatus::SUCCESS)
742+
status = ReadStatus::PARSE_ERROR;
743+
last_read_status = status;
744+
return inval;
745+
}
746+
last_read_status = status;
686747
simtime = simtime > inval[0] ? simtime : inval[0];
687748
s += port_name;
688749
inval.erase(inval.begin());
@@ -736,6 +797,13 @@ class Concore{
736797
return read_ZMQ(port_name, name, initstr);
737798
}
738799

800+
ReadResult read_result(string port_name, string name, string initstr) {
801+
ReadResult result;
802+
result.data = read(port_name, name, initstr);
803+
result.status = last_read_status;
804+
return result;
805+
}
806+
739807
/**
740808
* @brief deviate the write to ZMQ communication protocol when port identifier is a string key.
741809
* @param port_name The ZMQ port name.

concore_base.hpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -345,10 +345,11 @@ inline std::map<std::string, std::string> load_params(const std::string& params_
345345

346346
// Otherwise convert semicolon-separated key=value to dict format
347347
// e.g. "a=1;b=2" -> {"a":"1","b":"2"}
348+
std::string normalized = std::regex_replace(sparams, std::regex(";"), ",");
348349
std::string converted = "{\"" +
349350
std::regex_replace(
350351
std::regex_replace(
351-
std::regex_replace(sparams, std::regex(","), ",\""),
352+
std::regex_replace(normalized, std::regex(","), ",\""),
352353
std::regex("="), "\":"),
353354
std::regex(" "), "") +
354355
"}";

0 commit comments

Comments
 (0)