iCub-main
Loading...
Searching...
No Matches
serviceParser.cpp
Go to the documentation of this file.
1
2// -*- mode:C++; tab-width:4; c-basic-offset:4; indent-tabs-mode:nil -*-
3
4/*
5* Copyright (C) 2016 Robotcub Consortium
6* Author: Marco Accame
7* CopyPolicy: Released under the terms of the GNU GPL v2.0.
8*
9*/
10
11// general purpose stuff.
12#include <string>
13#include <iostream>
14#include <string.h>
15
16// Yarp Includes
17#include <yarp/os/Time.h>
18#include <yarp/os/Log.h>
19#include <yarp/os/LogStream.h>
20#include <stdarg.h>
21#include <stdio.h>
22#include <yarp/dev/PolyDriver.h>
23#include <ace/config.h>
24#include <ace/Log_Msg.h>
25
26
27// specific to this device driver.
28#include <serviceParser.h>
29
30#include <yarp/os/LogStream.h>
31#include "EoAnalogSensors.h"
32
33#include "EoProtocol.h"
34#include "EoProtocolMN.h"
35#include "EoProtocolAS.h"
36
37#include <yarp/os/NetType.h>
38
39#ifdef WIN32
40#pragma warning(once:4355)
41#endif
42
43
44
45using namespace yarp;
46using namespace yarp::os;
47using namespace yarp::dev;
48using namespace std;
49
50
52{
53 // how do i reset variable as_service?
54
55
56 as_service.type = eomn_serv_NONE;
57
60
63}
64
65bool ServiceParser::convert(std::string const &fromstring, eOmn_serv_type_t& toservicetype, bool& formaterror)
66{
67 const char *t = fromstring.c_str();
68
69 toservicetype = eomn_string2servicetype(t);
70
71 if(eomn_serv_UNKNOWN == toservicetype)
72 {
73 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOmn_serv_type_t";
74 formaterror = true;
75 return false;
76 }
77
78 return true;
79
80}
81
82bool ServiceParser::convert(std::string const &fromstring, eOmn_serv_diagn_mode_t &todiagnmode, bool &formaterror)
83{
84 const char *t = fromstring.c_str();
85
86 todiagnmode = eomn_string2servicediagnmode(t);
87
88 if(eomn_serv_diagn_mode_UNKNOWN == todiagnmode)
89 {
90 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOmn_serv_diagn_mode_t";
91 formaterror = true;
92 return false;
93 }
94
95 return true;
96}
97
98
99
100// bool ServiceParser::convert(std::string const &fromstring, eOmc_ctrlboard_t &controllerboard, bool &formaterror)
101// {
102// const char *t = fromstring.c_str();
103// eObool_t usecompactstring = eobool_false;
104// controllerboard = eomc_string2controllerboard(t, usecompactstring);
105//
106// if(eomc_ctrlboard_unknown == controllerboard)
107// { // attempting to retrieve the compact form
108// usecompactstring = eobool_true;
109// controllerboard = eomc_string2controllerboard(t, usecompactstring);
110// }
111//
112// if(eomc_ctrlboard_unknown == controllerboard)
113// {
114// yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOmc_ctrlboard_t";
115// formaterror = true;
116// return false;
117// }
118//
119// return true;
120// }
121
122bool ServiceParser::convert(std::string const &fromstring, eOas_sensor_t &tosensortype, bool &formaterror)
123{
124 const char *t = fromstring.c_str();
125
126 tosensortype = eoas_string2sensor(t);
127
128 if(eoas_unknown == tosensortype)
129 {
130 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOas_sensor_t";
131 formaterror = true;
132 return false;
133 }
134
135 return true;
136}
137
138
139bool ServiceParser::convert(std::string const &fromstring, eObrd_type_t& tobrdtype, bool& formaterror)
140{
141 const char *t = fromstring.c_str();
142
143 eObool_t usecompactstring = eobool_false;
144 tobrdtype = eoboards_string2type2(t, usecompactstring);
145
146 if(eobrd_unknown == tobrdtype)
147 {
148 usecompactstring = eobool_true;
149 tobrdtype = eoboards_string2type2(t, usecompactstring);
150 }
151
152 if(eobrd_unknown == tobrdtype)
153 {
154 yWarning() << "ServiceParser::convert(): string" << t << "cannot be converted into a proper eObrd_type_t";
155 formaterror = true;
156 return false;
157 }
158
159 return true;
160}
161
162
163bool ServiceParser::convert(std::string const &fromstring, eOmc_pidoutputtype_t& pidoutputtype, bool& formaterror)
164{
165 const char *t = fromstring.c_str();
166
167 eObool_t usecompactstring = eobool_false;
168 pidoutputtype = eomc_string2pidoutputtype(t, usecompactstring);
169
170 if(eomc_pidoutputtype_unknown == pidoutputtype)
171 {
172 usecompactstring = eobool_true;
173 pidoutputtype = eomc_string2pidoutputtype(t, usecompactstring);
174 }
175
176 if(eomc_pidoutputtype_unknown == pidoutputtype)
177 {
178 yWarning() << "ServiceParser::convert(): string" << t << "cannot be converted into a proper eOmc_pidoutputtype_t";
179 formaterror = true;
180 return false;
181 }
182
183 return true;
184}
185
186bool ServiceParser::convert(std::string const &fromstring, eOmc_jsetconstraint_t &jsetconstraint, bool& formaterror)
187{
188 const char *t = fromstring.c_str();
189
190 eObool_t usecompactstring = eobool_false;
191 jsetconstraint = eomc_string2jsetconstraint(t, usecompactstring);
192
193 if(eomc_jsetconstraint_unknown == jsetconstraint)
194 {
195 usecompactstring = eobool_true;
196 jsetconstraint = eomc_string2jsetconstraint(t, usecompactstring);
197 }
198
199 if(eomc_jsetconstraint_unknown == jsetconstraint)
200 {
201 yWarning() << "ServiceParser::convert(): string" << t << "cannot be converted into a proper eOmc_jsetconstraint_t";
202 formaterror = true;
203 return false;
204 }
205
206 return true;
207}
208
209bool ServiceParser::convert(std::string const &fromstring, eObrd_cantype_t& tobrdcantype, bool& formaterror)
210{
211 const char *t = fromstring.c_str();
212
213 eObool_t usecompactstring = eobool_false;
214 eObrd_type_t type = eoboards_string2type2(t, usecompactstring);
215
216 if(eobrd_unknown == type)
217 {
218 usecompactstring = eobool_true;
219 type = eoboards_string2type2(t, usecompactstring);
220 }
221
222 if(eobrd_unknown == type)
223 {
224 yWarning() << "ServiceParser::convert(): string" << t << "cannot be converted into a proper eObrd_type_t";
225 formaterror = true;
226 return false;
227 }
228
229 tobrdcantype = eoboards_type2cantype(type);
230 if(eobrd_cantype_unknown == tobrdcantype)
231 {
232 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eObrd_cantype_t";
233 formaterror = true;
234 return false;
235 }
236
237 return true;
238}
239
240bool ServiceParser::convert(std::string const &fromstring, eObrd_ethtype_t& tobrdethtype, bool& formaterror)
241{
242 const char *t = fromstring.c_str();
243
244 eObool_t usecompactstring = eobool_false;
245 eObrd_type_t type = eoboards_string2type2(t, usecompactstring);
246
247 if(eobrd_unknown == type)
248 {
249 usecompactstring = eobool_true;
250 type = eoboards_string2type2(t, usecompactstring);
251 }
252
253 if(eobrd_unknown == type)
254 {
255 yWarning() << "ServiceParser::convert(): string" << t << "cannot be converted into a proper eObrd_type_t";
256 formaterror = true;
257 return false;
258 }
259
260 tobrdethtype = eoboards_type2ethtype(type);
261 if(eobrd_ethtype_unknown == tobrdethtype)
262 {
263 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eObrd_ethtype_t";
264 formaterror = true;
265 return false;
266 }
267
268 return true;
269}
270
271
272bool ServiceParser::convert(std::string const &fromstring, bool& tobool, bool& formaterror)
273{
274 const char *t = fromstring.c_str();
275
276 if(0 == strcmp(t, "true"))
277 {
278 tobool = true;
279 }
280 else if(0 == strcmp(t, "false"))
281 {
282 tobool = false;
283 }
284 else if(0 == strcmp(t, "TRUE"))
285 {
286 tobool = true;
287 }
288 else if(0 == strcmp(t, "FALSE"))
289 {
290 tobool = false;
291 }
292 else if(0 == strcmp(t, "1"))
293 {
294 tobool = true;
295 }
296 else if(0 == strcmp(t, "0"))
297 {
298 tobool = false;
299 }
300 else
301 {
302 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for bool";
303 tobool = false;
304 formaterror = true;
305 return false;
306 }
307
308 return true;
309}
310
311
312bool ServiceParser::convert(const int number, uint8_t& tou8, bool& formaterror)
313{
314 if((number >= 0) && (number < 256))
315 {
316 tou8 = number;
317 }
318 else
319 {
320 yWarning() << "ServiceParser::convert():" << number << "is not a legal value for uint8_t";
321 tou8 = 0;
322 formaterror = true;
323 return false;
324 }
325
326 return true;
327}
328
329bool ServiceParser::convert(const int number, uint16_t& tou16, bool& formaterror)
330{
331 if((number >= 0) && (number < (64*1024)))
332 {
333 tou16 = number;
334 }
335 else
336 {
337 yWarning() << "ServiceParser::convert():" << number << "is not a legal value for uint16_t";
338 tou16 = 0;
339 formaterror = true;
340 return false;
341 }
342
343 return true;
344}
345
346
347
348bool ServiceParser::convert(std::string const &fromstring, const uint8_t strsize, char *str, bool &formaterror)
349{
350 const char *t = fromstring.c_str();
351
352 if((NULL == str) || (0 == strsize))
353 {
354 yWarning() << "ServiceParser::convert(): there is an attempt to convert string" << t << "into a NULL or zero-sized char *str: len = " << strsize;
355 formaterror = true;
356 return false;
357 }
358
359 if(strsize >= strlen(t))
360 {
361 snprintf(str, strsize, "%s", t);
362 }
363 else
364 {
365 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a char[] of max size" << strsize;
366 formaterror = true;
367 return false;
368 }
369
370 return true;
371}
372
373
374bool ServiceParser::convert(std::string const &fromstring, string &str, bool &formaterror)
375{
376 const char *t = fromstring.c_str();
377
378 if(0 != strlen(t))
379 {
380 str = t;
381 }
382 else
383 {
384 yWarning() << "ServiceParser::convert():" << t << "is not a legal string";
385 formaterror = true;
386 return false;
387 }
388
389 return true;
390}
391
392
393
394bool ServiceParser::convert(std::string const &fromstring, eObrd_location_t &location, bool &formaterror)
395{
396 // it is actually a micro-parser: PRE-num
397 // at
398
399 const char *t = fromstring.c_str();
400 int len = strlen(t);
401
402 if(len > 15)
403 {
404 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eObrd_location_t because it is too long with size = " << len;
405 formaterror = true;
406 return false;
407 }
408
409 char prefix[16] = {0};
410 sscanf(t, "%3c", prefix);
411 if(0 == strcmp(prefix, "ETH"))
412 {
413 int adr = 0;
414 sscanf(t, "%3c:%d", prefix, &adr);
415 location.any.place = eobrd_place_eth;
416 location.eth.id = adr;
417 }
418 else if(0 == strcmp(prefix, "CAN"))
419 {
420 int bus = 0;
421 int adr = 0;
422 char cc = 'x';
423 int sub = 9;
424 int numberofreaditems = sscanf(t, "%3c%d:%d%c%d", prefix, &bus, &adr, &cc, &sub);
425
426 if((3 != numberofreaditems) && (5 != numberofreaditems))
427 {
428 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eObrd_location_t because we dont have correct number of sections separated by :";
429 formaterror = true;
430 return false;
431 }
432
433 // verify bus being eitehr 1 or 2, and adr being 1 ----- 14
434 if((1 != bus) && (2 != bus))
435 {
436 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eObrd_location_t because we can have either CAN1 or CAN2";
437 formaterror = true;
438 return false;
439 }
440 if((0 == adr) || (adr > 14))
441 {
442 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eObrd_location_t because CAN address is in range [1, 14]";
443 formaterror = true;
444 return false;
445 }
446
447 location.any.place = (3 == numberofreaditems) ? (eobrd_place_can) : (eobrd_place_extcan);
448 if(eobrd_place_can == location.any.place)
449 {
450 location.can.port = (1 == bus) ? (eOcanport1) : (eOcanport2);
451 location.can.addr = adr;
452 location.can.ffu = 0;
453 }
454 else
455 {
456 location.extcan.port = (1 == bus) ? (eOcanport1) : (eOcanport2);
457 location.extcan.addr = adr;
458 if((eobrd_caninsideindex_first != sub) && (eobrd_caninsideindex_second != sub) && (eobrd_caninsideindex_third != sub) && (eobrd_caninsideindex_fourth != sub))
459 {
460 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eObrd_location_t because in CANx:adr:SUB, SUB address must be in range [0, 3]";
461 formaterror = true;
462 return false;
463 }
464 location.extcan.index = sub;
465 }
466
467 }
468 else if(0 == strcmp(prefix, "LOC"))
469 {
470 //Add here parsing for local port (both PWM port (P7, P8, etc and "index_proximal"for hand))
471 //in xml file we have: LOC:P7 or LOC:index_proximal
472
473 }
474 else
475 {
476 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eObrd_location_t because it does not begin with ETH or CAN";
477 formaterror = true;
478 return false;
479 }
480
481 return true;
482}
483
484bool ServiceParser::convert(eObrd_location_t const &loc, char *str, int len)
485{
486 if((NULL == str) || (0 == len))
487 {
488 return false;
489 }
490
491 if(eobrd_place_can == loc.any.place)
492 {
493 snprintf(str, len, "CAN%d:%d", (eOcanport1 == loc.can.port) ? 1 : 2, loc.can.addr);
494 }
495 else if(eobrd_place_extcan == loc.any.place)
496 {
497 snprintf(str, len, "CAN%d:%d:%d", (eOcanport1 == loc.extcan.port) ? 1 : 2, loc.extcan.addr, loc.extcan.index);
498 }
499 else if(eobrd_place_eth == loc.any.place)
500 { // it must be eobrd_place_eth
501 snprintf(str, len, "ETH:%d", loc.eth.id);
502 }
503 else
504 {
505 return false;
506 }
507
508 return true;
509}
510
511bool ServiceParser::convert(std::string const &fromstring, eOlocation_t &location, bool &formaterror)
512{
513 // it is actually a micro-parser: PRE-num
514
515 const char *t = fromstring.c_str();
516 int len = strlen(t);
517
518 if(len > 15)
519 {
520 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eOlocation_t because it is too long with size = " << len;
521 formaterror = true;
522 return false;
523 }
524
525 char prefix[16] = {0};
526 sscanf(t, "%3c", prefix);
527 if(0 == strcmp(prefix, "LOC"))
528 {
529 int adr = 0;
530 sscanf(t, "%3c:%d", prefix, &adr);
531 location.bus = eobus_local;
532 location.ffu = 0;
533 location.adr = adr;
534 }
535 else if((0 == strcmp(prefix, "CAN")) || (0 == strcmp(prefix, "ICC")))
536 {
537 int bus = 0;
538 int adr = 0;
539 int numberofreaditems = sscanf(t, "%3c%d:%d", prefix, &bus, &adr);
540
541 if(3 != numberofreaditems)
542 {
543 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eOlocation_t because we dont have correct number of sections separated by :";
544 formaterror = true;
545 return false;
546 }
547
548 // verify bus being eitehr 1 or 2, and adr being 1 ----- 14
549 if((1 != bus) && (2 != bus))
550 {
551 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eOlocation_t because we can have either ---1 or ---2";
552 formaterror = true;
553 return false;
554 }
555
556 if((0 == adr) || (adr > 14))
557 {
558 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eOlocation_t because address is not in range [1, 14]";
559 formaterror = true;
560 return false;
561 }
562
563 location.ffu = 0;
564 if(0 == strcmp(prefix, "CAN"))
565 {
566 location.bus = (1 == bus) ? eobus_can1 : eobus_can2;
567 }
568 else if(0 == strcmp(prefix, "ICC"))
569 {
570 location.bus = (1 == bus) ? eobus_icc1 : eobus_icc2;
571 }
572
573 location.adr = adr;
574
575 }
576 else
577 {
578 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for a eOlocation_t because it does not begin with LOC, CAN, ICC";
579 formaterror = true;
580 return false;
581 }
582
583 return true;
584}
585
586bool ServiceParser::convert(eOlocation_t const &loc, char *str, int len)
587{
588 if((NULL == str) || (0 == len))
589 {
590 return false;
591 }
592
593 if(eobus_can1 == loc.bus)
594 {
595 snprintf(str, len, "CAN1:%d", loc.adr);
596 }
597 else if(eobus_can2 == loc.bus)
598 {
599 snprintf(str, len, "CAN2:%d", loc.adr);
600 }
601 else if(eobus_local == loc.bus)
602 {
603 snprintf(str, len, "LOC:%d", loc.adr);
604 }
605 else if(eobus_icc1 == loc.bus)
606 {
607 snprintf(str, len, "ICC1:%d", loc.adr);
608 }
609 else if(eobus_icc2 == loc.bus)
610 {
611 snprintf(str, len, "ICC2:%d", loc.adr);
612 }
613 else
614 {
615 return false;
616 }
617
618 return true;
619}
620
621bool ServiceParser::convert(eObrd_canlocation_t const &canloc, char *str, int len)
622{
623 if((NULL == str) || (0 == len))
624 {
625 return false;
626 }
627
628 if(eobrd_caninsideindex_none == canloc.insideindex)
629 {
630 snprintf(str, len, "CAN%d:%d", (eOcanport1 == canloc.port) ? 1 : 2, canloc.addr);
631 }
632 else
633 {
634 snprintf(str, len, "CAN%d:%d:%d", (eOcanport1 == canloc.port) ? 1 : 2, canloc.addr, canloc.insideindex);
635 }
636
637 return true;
638}
639
640bool ServiceParser::convert(eObrd_firmwareversion_t const &firm, char *str, int len)
641{
642 if((NULL == str) || (0 == len))
643 {
644 return false;
645 }
646
647 snprintf(str, len, "(%d, %d, %d)", firm.major, firm.minor, firm.build);
648
649 return true;
650}
651
652bool ServiceParser::convert(eObrd_protocolversion_t const &prot, char *str, int len)
653{
654 if((NULL == str) || (0 == len))
655 {
656 return false;
657 }
658
659 snprintf(str, len, "(%d, %d)", prot.major, prot.minor);
660
661 return true;
662}
663
664bool ServiceParser::check_analog(Searchable &config, eOmn_serv_type_t type)
665{
666 bool formaterror = false;
667 // so far we check for eomn_serv_AS_mais / strain / inertials3 / psc / pos only
668 if((eomn_serv_AS_mais != type) && (eomn_serv_AS_strain != type) &&
669 (eomn_serv_AS_inertials3 != type) && (eomn_serv_AS_psc != type) && (eomn_serv_AS_pos != type))
670 {
671 yError() << "ServiceParser::check_analog() is called with wrong type";
672 return false;
673 }
674
675 // i parse the global board versions. if section is not found we can safely continue but we have boards.size() equal to zero.
676
677 // format is SERVICE{ type, PROPERTIES{ CANBOARDS, SENSORS }, SETTINGS }
678
679 Bottle b_SERVICE(config.findGroup("SERVICE"));
680 if(b_SERVICE.isNull())
681 {
682 yError() << "ServiceParser::check_analog() cannot find SERVICE group";
683 return false;
684 }
685
686 // check whether we have the proper type
687
688 if(false == b_SERVICE.check("type"))
689 {
690 yError() << "ServiceParser::check_analog() cannot find SERVICE.type";
691 return false;
692 }
693 else
694 {
695 Bottle b_type(b_SERVICE.find("type").asString());
696 if(false == convert(b_type.toString(), as_service.type, formaterror))
697 {
698 yError() << "ServiceParser::check_analog() has found unknown SERVICE.type = " << b_type.toString();
699 return false;
700 }
701 if(type != as_service.type)
702 {
703 yError() << "ServiceParser::check_analog() has found wrong SERVICE.type = " << as_service.type << "it must be" << "TODO: tostring() function";
704 return false;
705 }
706 }
707
708 // check whether we have the proper groups
709
710 Bottle b_PROPERTIES = Bottle(b_SERVICE.findGroup("PROPERTIES"));
711 if(b_PROPERTIES.isNull())
712 {
713 yError() << "ServiceParser::check_analog() cannot find PROPERTIES";
714 return false;
715 }
716 else
717 {
718 Bottle b_PROPERTIES_CANBOARDS = Bottle(b_PROPERTIES.findGroup("CANBOARDS"));
719 if(b_PROPERTIES_CANBOARDS.isNull())
720 {
721 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS";
722 return false;
723 }
724 else
725 {
726 // now get type, PROTOCOL.major/minor, FIRMWARE.major/minor/build and see their sizes. the must be all equal.
727 // for mais and strain and so far for intertials it must be numboards = 1.
728
729 Bottle b_PROPERTIES_CANBOARDS_type = b_PROPERTIES_CANBOARDS.findGroup("type");
730 if(b_PROPERTIES_CANBOARDS_type.isNull())
731 {
732 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.type";
733 return false;
734 }
735 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL = Bottle(b_PROPERTIES_CANBOARDS.findGroup("PROTOCOL"));
736 if(b_PROPERTIES_CANBOARDS_PROTOCOL.isNull())
737 {
738 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.PROTOCOL";
739 return false;
740 }
741 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL_major = Bottle(b_PROPERTIES_CANBOARDS_PROTOCOL.findGroup("major"));
742 if(b_PROPERTIES_CANBOARDS_PROTOCOL_major.isNull())
743 {
744 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.PROTOCOL.major";
745 return false;
746 }
747 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL_minor = Bottle(b_PROPERTIES_CANBOARDS_PROTOCOL.findGroup("minor"));
748 if(b_PROPERTIES_CANBOARDS_PROTOCOL_minor.isNull())
749 {
750 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.PROTOCOL.minor";
751 return false;
752 }
753 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE = Bottle(b_PROPERTIES_CANBOARDS.findGroup("FIRMWARE"));
754 if(b_PROPERTIES_CANBOARDS_FIRMWARE.isNull())
755 {
756 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.FIRMWARE";
757 return false;
758 }
759 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_major = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("major"));
760 if(b_PROPERTIES_CANBOARDS_FIRMWARE_major.isNull())
761 {
762 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.FIRMWARE.major";
763 return false;
764 }
765 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_minor = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("minor"));
766 if(b_PROPERTIES_CANBOARDS_FIRMWARE_minor.isNull())
767 {
768 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.FIRMWARE.minor";
769 return false;
770 }
771 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_build = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("build"));
772 if(b_PROPERTIES_CANBOARDS_FIRMWARE_build.isNull())
773 {
774 yError() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS.FIRMWARE.build";
775 return false;
776 }
777
778 size_t tmp = b_PROPERTIES_CANBOARDS_type.size();
779 int numboards = tmp - 1; // first position of bottle contains the tag "type"
780
781 // check if all other fields have the same size.
782 if( (tmp != b_PROPERTIES_CANBOARDS_PROTOCOL_major.size()) ||
783 (tmp != b_PROPERTIES_CANBOARDS_PROTOCOL_minor.size()) ||
784 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_major.size()) ||
785 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_minor.size()) ||
786 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_build.size())
787 )
788 {
789 yError() << "ServiceParser::check_analog() in PROPERTIES.CANBOARDS some param has inconsistent length";
790 return false;
791 }
792
793
795
796 formaterror = false;
797 for(int i=0; i<numboards; i++)
798 {
799 servCanBoard_t item;
800
801 convert(b_PROPERTIES_CANBOARDS_type.get(i+1).asString(), item.type, formaterror);
802 convert(b_PROPERTIES_CANBOARDS_PROTOCOL_major.get(i+1).asInt32(), item.protocol.major, formaterror);
803 convert(b_PROPERTIES_CANBOARDS_PROTOCOL_minor.get(i+1).asInt32(), item.protocol.minor, formaterror);
804
805 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_major.get(i+1).asInt32(), item.firmware.major, formaterror);
806 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_minor.get(i+1).asInt32(), item.firmware.minor, formaterror);
807 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_build.get(i+1).asInt32(), item.firmware.build, formaterror);
808
809 as_service.properties.canboards.push_back(item);
810 }
811
812 // in here we could decide to return false if any previous conversion function has returned error
813 // bool fromStringToBoolean(string str, bool &anyerror); // inside: if error then .... be sure to set error = true. dont set it to false.
814
815 if(true == formaterror)
816 {
817 yError() << "ServiceParser::check_analog() has detected an illegal format for some of the params of PROPERTIES.CANBOARDS some param has inconsistent length";
818 return false;
819 }
820 }
821
822 Bottle b_PROPERTIES_SENSORS = Bottle(b_PROPERTIES.findGroup("SENSORS"));
823 if(b_PROPERTIES_SENSORS.isNull())
824 {
825 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS";
826 return false;
827 }
828 else
829 {
830
831 Bottle b_PROPERTIES_SENSORS_id = Bottle(b_PROPERTIES_SENSORS.findGroup("id"));
832 if(b_PROPERTIES_SENSORS_id.isNull())
833 {
834 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.id";
835 return false;
836 }
837 Bottle b_PROPERTIES_SENSORS_type = Bottle(b_PROPERTIES_SENSORS.findGroup("type"));
838 if(b_PROPERTIES_SENSORS_type.isNull())
839 {
840 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.type";
841 return false;
842 }
843 Bottle b_PROPERTIES_SENSORS_location = Bottle(b_PROPERTIES_SENSORS.findGroup("location"));
844 if(b_PROPERTIES_SENSORS_location.isNull())
845 {
846 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.location";
847 return false;
848 }
849 Bottle b_PROPERTIES_SENSORS_frameName = Bottle(b_PROPERTIES_SENSORS.findGroup("framename"));
850 if(b_PROPERTIES_SENSORS_frameName.isNull() && eoas_string2sensor(b_PROPERTIES_SENSORS_type.get(1).asString().c_str())==eoas_strain)
851 {
852 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.framename";
853 }
854 Bottle b_PROPERTIES_SENSORS_sensorName = Bottle(b_PROPERTIES_SENSORS.findGroup("sensorName"));
855 if(b_PROPERTIES_SENSORS_sensorName.isNull())
856 {
857 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.sensorName";
858 }
859 Bottle b_PROPERTIES_SENSORS_boardType;
860 if((eomn_serv_AS_inertials3 == type) || (eomn_serv_AS_pos == type))
861 {
862
863 b_PROPERTIES_SENSORS_boardType = Bottle(b_PROPERTIES_SENSORS.findGroup("boardType"));
864 if(b_PROPERTIES_SENSORS_boardType.isNull())
865 {
866 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.boardType";
867 return false;
868 }
869 }
870 else
871 {
872 b_PROPERTIES_SENSORS_boardType.clear();
873 }
874
875 Bottle b_PROPERTIES_SENSORS_pos_port;
876 Bottle b_PROPERTIES_SENSORS_pos_connector;
877 Bottle b_PROPERTIES_SENSORS_pos_CALIBRATION;
878 Bottle b_PROPERTIES_SENSORS_pos_CALIBRATION_type;
879 Bottle b_PROPERTIES_SENSORS_pos_CALIBRATION_rotation;
880 Bottle b_PROPERTIES_SENSORS_pos_CALIBRATION_offset;
881 Bottle b_PROPERTIES_SENSORS_pos_CALIBRATION_invertDirection;
882
883 // add params proper only of POS
884 if(type == eomn_serv_AS_pos)
885 {
886 b_PROPERTIES_SENSORS_pos_port = Bottle(b_PROPERTIES_SENSORS.findGroup("port"));
887 if(b_PROPERTIES_SENSORS_pos_port.isNull())
888 {
889 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.port";
890 return false;
891 }
892
893 b_PROPERTIES_SENSORS_pos_connector = Bottle(b_PROPERTIES_SENSORS.findGroup("connector"));
894 if(b_PROPERTIES_SENSORS_pos_connector.isNull())
895 {
896 yError() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.connector";
897 return false;
898 }
899
900 b_PROPERTIES_SENSORS_pos_CALIBRATION = Bottle(b_PROPERTIES_SENSORS.findGroup("CALIBRATION"));
901 if(b_PROPERTIES_SENSORS_pos_CALIBRATION.isNull())
902 {
903 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.CALIBRATION. Using neutral values (ROT:zero, 0.0, false)";
904 }
905 else
906 {
907 b_PROPERTIES_SENSORS_pos_CALIBRATION_type = Bottle(b_PROPERTIES_SENSORS_pos_CALIBRATION.findGroup("type"));
908 if(b_PROPERTIES_SENSORS_pos_CALIBRATION_type.isNull())
909 {
910 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.CALIBRATION.type. Using value TYPE::decideg";
911 }
912
913 b_PROPERTIES_SENSORS_pos_CALIBRATION_rotation = Bottle(b_PROPERTIES_SENSORS_pos_CALIBRATION.findGroup("rotation"));
914 if(b_PROPERTIES_SENSORS_pos_CALIBRATION_rotation.isNull())
915 {
916 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.CALIBRATION.rotation. Using value ROT::zero";
917 }
918 b_PROPERTIES_SENSORS_pos_CALIBRATION_offset = Bottle(b_PROPERTIES_SENSORS_pos_CALIBRATION.findGroup("offset"));
919 if(b_PROPERTIES_SENSORS_pos_CALIBRATION_offset.isNull())
920 {
921 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.CALIBRATION.offset. Using value 0.0";
922 }
923 b_PROPERTIES_SENSORS_pos_CALIBRATION_invertDirection = Bottle(b_PROPERTIES_SENSORS_pos_CALIBRATION.findGroup("invertDirection"));
924 if(b_PROPERTIES_SENSORS_pos_CALIBRATION_invertDirection.isNull())
925 {
926 yWarning() << "ServiceParser::check_analog() cannot find PROPERTIES.SENSORS.CALIBRATION.invertDirection. Using value false";
927 }
928 }
929
930
931 }
932 else
933 {
934 b_PROPERTIES_SENSORS_pos_port.clear();
935 b_PROPERTIES_SENSORS_pos_connector.clear();
936 b_PROPERTIES_SENSORS_pos_CALIBRATION.clear();
937 b_PROPERTIES_SENSORS_pos_CALIBRATION_type.clear();
938 b_PROPERTIES_SENSORS_pos_CALIBRATION_rotation.clear();
939 b_PROPERTIES_SENSORS_pos_CALIBRATION_offset.clear();
940 b_PROPERTIES_SENSORS_pos_CALIBRATION_invertDirection.clear();
941 }
942
943 size_t tmp = b_PROPERTIES_SENSORS_id.size();
944 int numsensors = tmp - 1; // first position of bottle contains the tag "id"
945
946 // check if all other fields have the same size.
947 if( (tmp != b_PROPERTIES_SENSORS_type.size()) ||
948 (tmp != b_PROPERTIES_SENSORS_location.size()) ||
949 (((eomn_serv_AS_inertials3 == type) || (eomn_serv_AS_pos == type)) && (b_PROPERTIES_SENSORS_boardType.size() != tmp))
950 )
951 {
952 yError() << "ServiceParser::check_analog() xx in PROPERTIES.SENSORS some param has inconsistent length";
953 return false;
954 }
955
956
957 as_service.properties.sensors.resize(0);
958
959 formaterror = false;
960 for(int i=0; i<numsensors; i++)
961 {
962 servAnalogSensor_t item {};
963 item.clear();
964
965 convert(b_PROPERTIES_SENSORS_id.get(i+1).asString(), item.id, formaterror);
966 convert(b_PROPERTIES_SENSORS_type.get(i+1).asString(), item.type, formaterror);
967 convert(b_PROPERTIES_SENSORS_location.get(i+1).asString(), item.location, formaterror);
968 if(!b_PROPERTIES_SENSORS_frameName.isNull())
969 {
970 convert(b_PROPERTIES_SENSORS_frameName.get(i+1).asString(), item.frameName, formaterror);
971 }
972 if(!b_PROPERTIES_SENSORS_sensorName.isNull())
973 {
974 convert(b_PROPERTIES_SENSORS_sensorName.get(i+1).asString(), item.sensorName, formaterror);
975 }
976 if((eomn_serv_AS_inertials3 == type) || (eomn_serv_AS_pos == type))
977 {
978 convert(b_PROPERTIES_SENSORS_boardType.get(i+1).asString(), item.boardtype, formaterror);
979 }
980
981 if(eomn_serv_AS_pos == type)
982 {
983 // part which is present only in POS service
984 parse_POS_port(b_PROPERTIES_SENSORS_pos_port.get(i+1).asString(), item.pos.port, formaterror);
985 parse_POS_connector(b_PROPERTIES_SENSORS_pos_connector.get(i+1).asString(), item.boardtype, item.pos.connector, formaterror);
986
987 bool wehaveCALIBRATION = b_PROPERTIES_SENSORS_pos_CALIBRATION.isNull() ? false : true;
988
989 item.pos.calibration.clear();
990 item.pos.calibration.type = eoas_pos_TYPE_decideg;
991
992 if(wehaveCALIBRATION)
993 {
994 // then we need to parse four values: type, rotation, offset, invertDirection
995
996 // type
997 if(false == b_PROPERTIES_SENSORS_pos_CALIBRATION_type.isNull())
998 {
999 parse_POS_CALIB_type(b_PROPERTIES_SENSORS_pos_CALIBRATION_type.get(i+1).asString(), item.pos.calibration.type, formaterror);
1000 }
1001
1002 // rotation
1003 if(false == b_PROPERTIES_SENSORS_pos_CALIBRATION_rotation.isNull())
1004 {
1005 parse_POS_CALIB_rotation(b_PROPERTIES_SENSORS_pos_CALIBRATION_rotation.get(i+1).asString(), item.pos.calibration.rotation, formaterror);
1006 }
1007
1008 // offset
1009 if(false == b_PROPERTIES_SENSORS_pos_CALIBRATION_offset.isNull())
1010 {
1011 item.pos.calibration.offset = b_PROPERTIES_SENSORS_pos_CALIBRATION_offset.get(i+1).asFloat32();
1012 }
1013
1014 // invertdirection
1015 if(false == b_PROPERTIES_SENSORS_pos_CALIBRATION_invertDirection.isNull())
1016 {
1017 item.pos.calibration.invertdirection = b_PROPERTIES_SENSORS_pos_CALIBRATION_invertDirection.get(i+1).asBool();
1018 }
1019
1020 }
1021
1022 }
1023
1024 as_service.properties.sensors.push_back(item);
1025 }
1026
1027 // in here we could decide to return false if any previous conversion function has returned error
1028 // bool fromStringToBoolean(string str, bool &anyerror); // inside: if error then .... be sure to set error = true. dont set it to false.
1029
1030 if(true == formaterror)
1031 {
1032 yError() << "ServiceParser::check_analog() has detected an illegal format for some of the params of PROPERTIES.SENSORS some param has inconsistent length";
1033 return false;
1034 }
1035
1036 }
1037
1038 }
1039
1040 Bottle b_SETTINGS = Bottle(b_SERVICE.findGroup("SETTINGS"));
1041 if(b_SETTINGS.isNull())
1042 {
1043 yError() << "ServiceParser::check_analog() cannot find SETTINGS";
1044 return false;
1045 }
1046 else
1047 {
1048
1049 Bottle b_SETTINGS_acquisitionRate = Bottle(b_SETTINGS.findGroup("acquisitionRate"));
1050 if(b_SETTINGS_acquisitionRate.isNull())
1051 {
1052 yError() << "ServiceParser::check_analog() cannot find SETTINGS.acquisitionRate";
1053 return false;
1054 }
1055 Bottle b_SETTINGS_enabledSensors = Bottle(b_SETTINGS.findGroup("enabledSensors"));
1056 if(b_SETTINGS_enabledSensors.isNull())
1057 {
1058 yError() << "ServiceParser::check_analog() cannot find SETTINGS.enabledSensors";
1059 return false;
1060 }
1061
1062 size_t s = b_SETTINGS_enabledSensors.size();
1063 size_t numenabledsensors = (0 == s) ? (0) : (s - 1) ; // first position of bottle contains the tag "enabledSensors"
1064
1065 // the enabled must be <= the sensors.
1066 if( numenabledsensors > as_service.properties.sensors.size() )
1067 {
1068 yError() << "ServiceParser::check_analog() in SETTINGS.enabledSensors there are too many items with respect to supported sensors:" << numenabledsensors << "vs." << as_service.properties.sensors.size();
1069 return false;
1070 }
1071
1072 convert(b_SETTINGS_acquisitionRate.get(1).asInt32(), as_service.settings.acquisitionrate, formaterror);
1073
1074
1076
1077 for(size_t i=0; i<numenabledsensors; i++)
1078 {
1079 servAnalogSensor_t founditem;
1080
1081 std::string s_enabled_id = b_SETTINGS_enabledSensors.get(i+1).asString();
1082// const char *str = s_enabled_id.c_str();
1083// std::string cpp_str = str;
1084
1085 // we must now search inside the whole vector<> as_service.properties.sensors if we find an id which matches s_enabled_id ....
1086 // if we dont, ... we issue a warning.
1087 // if we find, ... we do a pushback of it inside
1088 bool found = false;
1089 // i decide to use a brute force search ... for now
1090 for(size_t n=0; n<as_service.properties.sensors.size(); n++)
1091 {
1093 //if(item.id == cpp_str)
1094 if(item.id == s_enabled_id)
1095 {
1096 found = true;
1097 founditem = item;
1098 break;
1099 }
1100 }
1101
1102 if(true == found)
1103 {
1104 as_service.settings.enabledsensors.push_back(founditem);
1105 }
1106
1107 }
1108
1109 // in here we issue an error if we dont have at least one enabled sensor
1110
1111 if(0 == as_service.settings.enabledsensors.size())
1112 {
1113 yError() << "ServiceParser::check_analog() could not find any item in SETTINGS.enabledSensors which matches what in PROPERTIES.SENSORS.id";
1114 return false;
1115 }
1116
1117 }
1118
1119 // now we may have one or more sections which are specific of the device ...
1120
1121 // only strain so far.
1122
1123 if(eomn_serv_AS_strain == type)
1124 {
1125 Bottle b_STRAIN_SETTINGS = Bottle(b_SERVICE.findGroup("STRAIN_SETTINGS"));
1126 if(b_STRAIN_SETTINGS.isNull())
1127 {
1128 yError() << "ServiceParser::check_analog() cannot find STRAIN_SETTINGS";
1129 return false;
1130 }
1131 else
1132 {
1133
1134 Bottle b_STRAIN_SETTINGS_useCalibration = Bottle(b_STRAIN_SETTINGS.findGroup("useCalibration"));
1135 if(b_STRAIN_SETTINGS_useCalibration.isNull())
1136 {
1137 yError() << "ServiceParser::check_analog() cannot find STRAIN_SETTINGS.useCalibration";
1138 return false;
1139 }
1140
1141 formaterror = false;
1142 convert(b_STRAIN_SETTINGS_useCalibration.get(1).asString(), as_strain_settings.useCalibration, formaterror);
1143
1144 if(true == formaterror)
1145 {
1146 yError() << "ServiceParser::check_analog() has detected an illegal format for paramf STRAIN_SETTINGS.useCalibration";
1147 return false;
1148 }
1149 }
1150 }
1151
1152
1153
1154
1155 // we we are in here we have the struct filled with all variables ... some validations are still due to the calling device.
1156 // for instance, if embObjMais
1157
1158 return true;
1159}
1160
1161bool ServiceParser::check_skin(Searchable &config)
1162{
1163 const eOmn_serv_type_t type = eomn_serv_SK_skin;
1164 bool formaterror = false;
1165
1166 // the format so far is:
1167 // SERVICE{ type, PROPERTIES{ CANBOARDS } }
1168 // later on we can add SERVICE.PROPERTIES.SENSORS and SERVICE.SETTINGS
1169
1170 // however: if w dont have the SERVICE group we return false so that the caller can use default values
1171
1172
1173 Bottle b_SERVICE(config.findGroup("SERVICE"));
1174 if(b_SERVICE.isNull())
1175 {
1176 // yWarning() << "ServiceParser::check_skin() cannot find SERVICE group";
1177 return false;
1178 }
1179
1180 // check whether we have the proper type
1181
1182 if(false == b_SERVICE.check("type"))
1183 {
1184 // yWarning() << "ServiceParser::check_skin() cannot find SERVICE.type";
1185 return false;
1186 }
1187 else
1188 {
1189 Bottle b_type(b_SERVICE.find("type").asString());
1190 if(false == convert(b_type.toString(), sk_service.type, formaterror))
1191 {
1192 yWarning() << "ServiceParser::check_skin() has found unknown SERVICE.type = " << b_type.toString();
1193 return false;
1194 }
1195 if(type != sk_service.type)
1196 {
1197 yWarning() << "ServiceParser::check_skin() has found wrong SERVICE.type = " << sk_service.type << "it must be" << "TODO: tostring() function";
1198 return false;
1199 }
1200 }
1201
1202 // check whether we have the proper groups
1203
1204 Bottle b_PROPERTIES = Bottle(b_SERVICE.findGroup("PROPERTIES"));
1205 if(b_PROPERTIES.isNull())
1206 {
1207 yWarning() << "ServiceParser::check_skin() cannot find PROPERTIES";
1208 return false;
1209 }
1210 else
1211 {
1212 Bottle b_PROPERTIES_CANBOARDS = Bottle(b_PROPERTIES.findGroup("CANBOARDS"));
1213 if(b_PROPERTIES_CANBOARDS.isNull())
1214 {
1215 yWarning() << "ServiceParser::check() cannot find PROPERTIES.CANBOARDS";
1216 return false;
1217 }
1218 else
1219 {
1220 // now get type, PROTOCOL.major/minor, FIRMWARE.major/minor/build and see their sizes. the must be all equal.
1221 // for skin it must be numboards = 1.
1222
1223 Bottle b_PROPERTIES_CANBOARDS_type = b_PROPERTIES_CANBOARDS.findGroup("type");
1224 if(b_PROPERTIES_CANBOARDS_type.isNull())
1225 {
1226 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.type";
1227 return false;
1228 }
1229 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL = Bottle(b_PROPERTIES_CANBOARDS.findGroup("PROTOCOL"));
1230 if(b_PROPERTIES_CANBOARDS_PROTOCOL.isNull())
1231 {
1232 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.PROTOCOL";
1233 return false;
1234 }
1235 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL_major = Bottle(b_PROPERTIES_CANBOARDS_PROTOCOL.findGroup("major"));
1236 if(b_PROPERTIES_CANBOARDS_PROTOCOL_major.isNull())
1237 {
1238 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.PROTOCOL.major";
1239 return false;
1240 }
1241 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL_minor = Bottle(b_PROPERTIES_CANBOARDS_PROTOCOL.findGroup("minor"));
1242 if(b_PROPERTIES_CANBOARDS_PROTOCOL_minor.isNull())
1243 {
1244 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.PROTOCOL.minor";
1245 return false;
1246 }
1247 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE = Bottle(b_PROPERTIES_CANBOARDS.findGroup("FIRMWARE"));
1248 if(b_PROPERTIES_CANBOARDS_FIRMWARE.isNull())
1249 {
1250 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.FIRMWARE";
1251 return false;
1252 }
1253 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_major = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("major"));
1254 if(b_PROPERTIES_CANBOARDS_FIRMWARE_major.isNull())
1255 {
1256 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.FIRMWARE.major";
1257 return false;
1258 }
1259 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_minor = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("minor"));
1260 if(b_PROPERTIES_CANBOARDS_FIRMWARE_minor.isNull())
1261 {
1262 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.FIRMWARE.minor";
1263 return false;
1264 }
1265 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_build = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("build"));
1266 if(b_PROPERTIES_CANBOARDS_FIRMWARE_build.isNull())
1267 {
1268 yError() << "ServiceParser::check_skin() cannot find PROPERTIES.CANBOARDS.FIRMWARE.build";
1269 return false;
1270 }
1271
1272 size_t tmp = b_PROPERTIES_CANBOARDS_type.size();
1273 size_t numboards = (0 == tmp) ? 0 : (tmp - 1); // first position of bottle contains the tag "type"
1274
1275 // check if all other fields have the same size.
1276 if( (tmp != b_PROPERTIES_CANBOARDS_PROTOCOL_major.size()) ||
1277 (tmp != b_PROPERTIES_CANBOARDS_PROTOCOL_minor.size()) ||
1278 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_major.size()) ||
1279 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_minor.size()) ||
1280 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_build.size())
1281 )
1282 {
1283 yError() << "ServiceParser::check_skin() in PROPERTIES.CANBOARDS some param has inconsistent length";
1284 return false;
1285 }
1286
1287 if(1 != numboards)
1288 {
1289 yError() << "ServiceParser::check_skin() in PROPERTIES.CANBOARDS has found more than one board";
1290 return false;
1291 }
1292
1293 formaterror = false;
1294
1296
1297 convert(b_PROPERTIES_CANBOARDS_type.get(1).asString(), sk_service.properties.canboard.type, formaterror);
1298 convert(b_PROPERTIES_CANBOARDS_PROTOCOL_major.get(1).asInt32(), sk_service.properties.canboard.protocol.major, formaterror);
1299 convert(b_PROPERTIES_CANBOARDS_PROTOCOL_minor.get(1).asInt32(), sk_service.properties.canboard.protocol.minor, formaterror);
1300
1301 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_major.get(1).asInt32(), sk_service.properties.canboard.firmware.major, formaterror);
1302 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_minor.get(1).asInt32(), sk_service.properties.canboard.firmware.minor, formaterror);
1303 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_build.get(1).asInt32(), sk_service.properties.canboard.firmware.build, formaterror);
1304
1305
1306
1307 // in here we could decide to return false if any previous conversion function has returned error
1308 // bool fromStringToBoolean(string str, bool &anyerror); // inside: if error then .... be sure to set error = true. dont set it to false.
1309
1310 if(true == formaterror)
1311 {
1312 yError() << "ServiceParser::check_skin() has detected an illegal format for some of the params of PROPERTIES.CANBOARDS some param has inconsistent length";
1313 return false;
1314 }
1315 }
1316
1317#if 0
1318 // we dont have this group yet
1319
1320 Bottle b_PROPERTIES_SENSORS = Bottle(b_PROPERTIES.findGroup("SENSORS"));
1321 if(b_PROPERTIES_SENSORS.isNull())
1322 {
1323 yError() << "ServiceParser::check() cannot find PROPERTIES.SENSORS";
1324 return false;
1325 }
1326 else
1327 {
1328
1329 Bottle b_PROPERTIES_SENSORS_id = Bottle(b_PROPERTIES_SENSORS.findGroup("id"));
1330 if(b_PROPERTIES_SENSORS_id.isNull())
1331 {
1332 yError() << "ServiceParser::check() cannot find PROPERTIES.SENSORS.id";
1333 return false;
1334 }
1335 Bottle b_PROPERTIES_SENSORS_type = Bottle(b_PROPERTIES_SENSORS.findGroup("type"));
1336 if(b_PROPERTIES_SENSORS_type.isNull())
1337 {
1338 yError() << "ServiceParser::check() cannot find PROPERTIES.SENSORS.type";
1339 return false;
1340 }
1341 Bottle b_PROPERTIES_SENSORS_location = Bottle(b_PROPERTIES_SENSORS.findGroup("location"));
1342 if(b_PROPERTIES_SENSORS_location.isNull())
1343 {
1344 yError() << "ServiceParser::check() cannot find PROPERTIES.SENSORS.location";
1345 return false;
1346 }
1347 Bottle b_PROPERTIES_SENSORS_boardtype;
1348 if(type == eomn_serv_AS_inertials3)
1349 {
1350
1351 b_PROPERTIES_SENSORS_boardtype = Bottle(b_PROPERTIES_SENSORS.findGroup("boardType"));
1352 if(b_PROPERTIES_SENSORS_boardtype.isNull())
1353 {
1354 yError() << "ServiceParser::check() cannot find PROPERTIES.SENSORS.boardType";
1355 return false;
1356 }
1357 }
1358 else
1359 {
1360 b_PROPERTIES_SENSORS_boardtype.clear();
1361 }
1362
1363 int tmp = b_PROPERTIES_SENSORS_id.size();
1364 int numsensors = tmp - 1; // first position of bottle contains the tag "id"
1365
1366 // check if all other fields have the same size.
1367 if( (tmp != b_PROPERTIES_SENSORS_type.size()) ||
1368 (tmp != b_PROPERTIES_SENSORS_location.size()) ||
1369 ((type == eomn_serv_AS_inertials3) && (b_PROPERTIES_SENSORS_boardtype.size() != tmp))
1370 )
1371 {
1372 yError() << "ServiceParser::check() in PROPERTIES.SENSORS some param has inconsistent length";
1373 return false;
1374 }
1375
1376
1377 sk_service.properties.sensors.resize(0);
1378
1379 formaterror = false;
1380 for(int i=0; i<numsensors; i++)
1381 {
1382 servAnalogSensor_t item;
1383 item.type = eoas_none;
1384 item.location.any.place = eobrd_place_none;
1385
1386 convert(b_PROPERTIES_SENSORS_id.get(i+1).asString(), item.id, formaterror);
1387 convert(b_PROPERTIES_SENSORS_type.get(i+1).asString(), item.type, formaterror);
1388 convert(b_PROPERTIES_SENSORS_location.get(i+1).asString(), item.location, formaterror);
1389 if(type == eomn_serv_AS_inertials3)
1390 {
1391 convert(b_PROPERTIES_SENSORS_boardtype.get(i+1).asString(), item.boardtype, formaterror);
1392 }
1393 else
1394 {
1395 item.boardtype = eobrd_none;
1396 }
1397
1398 sk_service.properties.sensors.push_back(item);
1399 }
1400
1401 // in here we could decide to return false if any previous conversion function has returned error
1402 // bool fromStringToBoolean(string str, bool &anyerror); // inside: if error then .... be sure to set error = true. dont set it to false.
1403
1404 if(true == formaterror)
1405 {
1406 yError() << "ServiceParser::check() has detected an illegal format for some of the params of PROPERTIES.SENSORS some param has inconsistent length";
1407 return false;
1408 }
1409
1410 }
1411
1412#endif
1413
1414 }
1415
1416#if 0
1417
1418 // we dont have this group yet
1419
1420 Bottle b_SETTINGS = Bottle(b_SERVICE.findGroup("SETTINGS"));
1421 if(b_SETTINGS.isNull())
1422 {
1423 yError() << "ServiceParser::check() cannot find SETTINGS";
1424 return false;
1425 }
1426 else
1427 {
1428
1429 Bottle b_SETTINGS_acquisitionRate = Bottle(b_SETTINGS.findGroup("acquisitionRate"));
1430 if(b_SETTINGS_acquisitionRate.isNull())
1431 {
1432 yError() << "ServiceParser::check() cannot find SETTINGS.acquisitionRate";
1433 return false;
1434 }
1435 Bottle b_SETTINGS_enabledSensors = Bottle(b_SETTINGS.findGroup("enabledSensors"));
1436 if(b_SETTINGS_enabledSensors.isNull())
1437 {
1438 yError() << "ServiceParser::check() cannot find SETTINGS.enabledSensors";
1439 return false;
1440 }
1441
1442 int numenabledsensors = b_SETTINGS_enabledSensors.size() - 1; // first position of bottle contains the tag "enabledSensors"
1443
1444 // the enabled must be <= the sensors.
1445 if( numenabledsensors > sk_service.properties.sensors.size() )
1446 {
1447 yError() << "ServiceParser::check() in SETTINGS.enabledSensors there are too many items with respect to supported sensors:" << numenabledsensors << "vs." << sk_service.properties.sensors.size();
1448 return false;
1449 }
1450
1451 convert(b_SETTINGS_acquisitionRate.get(1).asInt32(), sk_service.settings.acquisitionrate, formaterror);
1452
1453
1454 sk_service.settings.enabledsensors.resize(0);
1455
1456 for(int i=0; i<numenabledsensors; i++)
1457 {
1458 servAnalogSensor_t founditem;
1459
1460 std::string s_enabled_id = b_SETTINGS_enabledSensors.get(i+1).asString();
1461// const char *str = s_enabled_id.c_str();
1462// std::string cpp_str = str;
1463
1464 // we must now search inside the whole vector<> sk_service.properties.sensors if we find an id which matches s_enabled_id ....
1465 // if we dont, ... we issue a warning.
1466 // if we find, ... we do a pushback of it inside
1467 bool found = false;
1468 // i decide to use a brute force search ... for now
1469 for(size_t n=0; n<sk_service.properties.sensors.size(); n++)
1470 {
1471 servAnalogSensor_t item = sk_service.properties.sensors.at(n);
1472 //if(item.id == cpp_str)
1473 if(item.id == s_enabled_id)
1474 {
1475 found = true;
1476 founditem = item;
1477 break;
1478 }
1479 }
1480
1481 if(true == found)
1482 {
1483 sk_service.settings.enabledsensors.push_back(founditem);
1484 }
1485
1486 }
1487
1488 // in here we issue an error if we dont have at least one enabled sensor
1489
1490 if(0 == sk_service.settings.enabledsensors.size())
1491 {
1492 yError() << "ServiceParser::check() could not find any item in SETTINGS.enabledSensors which matches what in PROPERTIES.SENSORS.id";
1493 return false;
1494 }
1495
1496 }
1497
1498#endif
1499
1500
1501#if 0
1502 // we dont have this group yet
1503 // now we may have one or more sections which are specific of the device ...
1504
1505
1506
1507 if(eomn_serv_AS_strain == type)
1508 {
1509 Bottle b_STRAIN_SETTINGS = Bottle(b_SERVICE.findGroup("STRAIN_SETTINGS"));
1510 if(b_STRAIN_SETTINGS.isNull())
1511 {
1512 yError() << "ServiceParser::check() cannot find STRAIN_SETTINGS";
1513 return false;
1514 }
1515 else
1516 {
1517
1518 Bottle b_STRAIN_SETTINGS_useCalibration = Bottle(b_STRAIN_SETTINGS.findGroup("useCalibration"));
1519 if(b_STRAIN_SETTINGS_useCalibration.isNull())
1520 {
1521 yError() << "ServiceParser::check() cannot find STRAIN_SETTINGS.useCalibration";
1522 return false;
1523 }
1524
1525 formaterror = false;
1526 convert(b_STRAIN_SETTINGS_useCalibration.get(1).asString(), sk_skin_settings.useCalibration, formaterror);
1527
1528 if(true == formaterror)
1529 {
1530 yError() << "ServiceParser::check() has detected an illegal format for paramf STRAIN_SETTINGS.useCalibration";
1531 return false;
1532 }
1533 }
1534 }
1535
1536
1537#endif
1538
1539
1540 // we we are in here we have the struct filled with all variables ... some validations are still due to the calling device.
1541
1542 return true;
1543}
1544
1545
1546
1547bool ServiceParser::parseService(Searchable &config, servConfigMais_t &maisconfig)
1548{
1549 if(false == check_analog(config, eomn_serv_AS_mais))
1550 {
1551 yError() << "ServiceParser::parseService() has received an invalid SERVICE group for mais";
1552 return false;
1553 }
1554
1555 // now we extract values ... so far we dont make many checks ... we just assume the vector<> are of size 1.
1556 servCanBoard_t themais_props = as_service.properties.canboards.at(0);
1558
1559
1560 // first check we do is about themais_props.type
1561 if(eobrd_cantype_mais != themais_props.type)
1562 {
1563 yError() << "ServiceParser::parseService() has detected an invalid type of board. it should be a eobrd_mais but is a:" << eoboards_type2string2(eoboards_cantype2type(themais_props.type), eobool_false);
1564 return false;
1565 }
1566
1568
1569 maisconfig.nameOfMais = themais_sensor.id;
1570
1571 memset(&maisconfig.ethservice.configuration, 0, sizeof(maisconfig.ethservice.configuration));
1572
1573 maisconfig.ethservice.configuration.type = eomn_serv_AS_mais;
1574 memcpy(&maisconfig.ethservice.configuration.data.as.mais.version.protocol, &themais_props.protocol, sizeof(eObrd_protocolversion_t));
1575 memcpy(&maisconfig.ethservice.configuration.data.as.mais.version.firmware, &themais_props.firmware, sizeof(eObrd_firmwareversion_t));
1576
1577 // second check we do is about themais_sensor.location
1578 if(eobrd_place_can != themais_sensor.location.any.place)
1579 {
1580 yError() << "ServiceParser::parseService() has received an invalid location for its mais. it is not a CANx:adr location";
1581 return false;
1582 }
1583 maisconfig.ethservice.configuration.data.as.mais.canloc.port = themais_sensor.location.can.port;
1584 maisconfig.ethservice.configuration.data.as.mais.canloc.addr = themais_sensor.location.can.addr;
1585 maisconfig.ethservice.configuration.data.as.mais.canloc.insideindex = eobrd_caninsideindex_none;
1586
1587
1588 return true;
1589}
1590
1591
1592bool ServiceParser::parseService(Searchable &config, servConfigStrain_t &strainconfig)
1593{
1594 if(false == check_analog(config, eomn_serv_AS_strain))
1595 {
1596 yError() << "ServiceParser::parseService() has received an invalid SERVICE group for strain";
1597 return false;
1598 }
1599
1600 // now we extract values ... so far we dont make many checks ... we just assume the vector<> are of size 1.
1601 servCanBoard_t thestrain_props = as_service.properties.canboards.at(0);
1602 servAnalogSensor_t thestrain_sensor = as_service.settings.enabledsensors.at(0);
1603
1604 // first check we do is about thestrain_props.type
1605 if((eobrd_cantype_strain != thestrain_props.type) && (eobrd_cantype_strain2 != thestrain_props.type) && (eobrd_cantype_strain2c != thestrain_props.type))
1606 {
1607 yError() << "ServiceParser::parseService() has detected an invalid type of board. it should be a eobrd_strain, eobrd_strain2 or eobrd_strain2c but is a:" << eoboards_type2string2(eoboards_cantype2type(thestrain_props.type), eobool_false);
1608 return false;
1609 }
1610
1613 strainconfig.nameOfStrain = thestrain_sensor.id;
1614
1615 memset(&strainconfig.ethservice.configuration, 0, sizeof(strainconfig.ethservice.configuration));
1616
1617 strainconfig.ethservice.configuration.type = eomn_serv_AS_strain;
1618 strainconfig.ethservice.configuration.data.as.strain.boardtype.type = thestrain_props.type;
1619 memcpy(&strainconfig.ethservice.configuration.data.as.strain.boardtype.protocol, &thestrain_props.protocol, sizeof(eObrd_protocolversion_t));
1620 memcpy(&strainconfig.ethservice.configuration.data.as.strain.boardtype.firmware, &thestrain_props.firmware, sizeof(eObrd_firmwareversion_t));
1621
1622 // second check we do is about thestrain_sensor.location
1623 if(eobrd_place_can != thestrain_sensor.location.any.place)
1624 {
1625 yError() << "ServiceParser::parseService() has received an invalid location for strain. it is not a CANx:adr location";
1626 return false;
1627 }
1628 strainconfig.ethservice.configuration.data.as.strain.canloc.port = thestrain_sensor.location.can.port;
1629 strainconfig.ethservice.configuration.data.as.strain.canloc.addr = thestrain_sensor.location.can.addr;
1630 strainconfig.ethservice.configuration.data.as.strain.canloc.insideindex = eobrd_caninsideindex_none;
1631
1632
1633
1634 return true;
1635}
1636
1637bool ServiceParser::parseService(Searchable &config, servConfigFTsensor_t &ftconfig)
1638{
1639 if(false == check_analog(config, eomn_serv_AS_strain))
1640 {
1641 yError() << "ServiceParser::parseService() has received an invalid SERVICE group for strain";
1642 return false;
1643 }
1644
1645 // now we extract values ... so far we dont make many checks ... we just assume the vector<> are of size 1.
1646 servCanBoard_t thestrain_props = as_service.properties.canboards.at(0);
1647 servAnalogSensor_t thestrain_sensor = as_service.settings.enabledsensors.at(0);
1648
1649 // first check we do is about thestrain_props.type
1650 if( (eobrd_cantype_strain != thestrain_props.type) && (eobrd_cantype_strain2 != thestrain_props.type) && (eobrd_cantype_strain2c != thestrain_props.type))
1651 {
1652 yError() << "ServiceParser::parseService() for embObjFTsensor has detected an invalid type of board. it should be a eobrd_strain2 or a eobrd_strain2c but is a:" << eoboards_type2string2(eoboards_cantype2type(thestrain_props.type), eobool_false);
1653 return false;
1654 }
1655
1658 ftconfig.nameOfStrain = thestrain_sensor.id;
1659 ftconfig.frameName = thestrain_sensor.frameName;
1660
1661 memset(&ftconfig.ethservice.configuration, 0, sizeof(ftconfig.ethservice.configuration));
1662
1663 ftconfig.ethservice.configuration.type = eomn_serv_AS_strain;
1664 ftconfig.ethservice.configuration.data.as.strain.boardtype.type = thestrain_props.type;
1665 memcpy(&ftconfig.ethservice.configuration.data.as.strain.boardtype.protocol, &thestrain_props.protocol, sizeof(eObrd_protocolversion_t));
1666 memcpy(&ftconfig.ethservice.configuration.data.as.strain.boardtype.firmware, &thestrain_props.firmware, sizeof(eObrd_firmwareversion_t));
1667
1668 // second check we do is about thestrain_sensor.location
1669 if(eobrd_place_can != thestrain_sensor.location.any.place)
1670 {
1671 yError() << "ServiceParser::parseService() has received an invalid location for strain. it is not a CANx:adr location";
1672 return false;
1673 }
1674 ftconfig.ethservice.configuration.data.as.strain.canloc.port = thestrain_sensor.location.can.port;
1675 ftconfig.ethservice.configuration.data.as.strain.canloc.addr = thestrain_sensor.location.can.addr;
1676 ftconfig.ethservice.configuration.data.as.strain.canloc.insideindex = eobrd_caninsideindex_none;
1677
1678
1679
1680 Bottle b_SERVICE(config.findGroup("SERVICE")); //b_SERVICE and b_SETTINGS could not be null, otherwise parseService function would have returned false
1681 Bottle b_SETTINGS = Bottle(b_SERVICE.findGroup("SETTINGS"));
1682 Bottle b_SETTINGS_temp = Bottle(b_SETTINGS.findGroup("temperature-acquisitionRate"));
1683 // Only strain2 and strain2c has temperature sensors.
1684 if(b_SETTINGS_temp.isNull())
1685 {
1686 if (eobrd_cantype_strain != thestrain_props.type) {
1687 yError() << "ServiceParser::parseService() for embObjFTsensor device cannot find SETTINGS.temperature-acquisitionRate";
1688 return false;
1689 }
1690 else {
1691 // If set to -1, embObjFTSensor disable the temperature.
1692 ftconfig.temperatureAcquisitionrate = -1;
1693 }
1694 }
1695 else
1696 {
1697 ftconfig.temperatureAcquisitionrate = b_SETTINGS_temp.get(1).asInt32();
1698 //TODO: chek that the acquisition rate is inside a reasonable range
1699 }
1700
1701 return true;
1702}
1703
1704bool ServiceParser::parseService(Searchable &config, servConfigImu_t &imuconfig)
1705{
1706 if(false == check_analog(config, eomn_serv_AS_inertials3))
1707 {
1708 yError() << "ServiceParser::parseService(IMU) has received an invalid SERVICE group for IMU";
1709 return false;
1710 }
1711
1712
1713 //check the num of type of boards. At max we have 4 board type (see eOas_inertials3_boardinfos_maxnumber)
1714
1715 if(as_service.properties.canboards.size() > eOas_inertials3_boardinfos_maxnumber)
1716 {
1717 yError() << "ServiceParser::parseService(IMU): too many type board info are configured. The max num is " << eOas_inertials3_boardinfos_maxnumber;
1718 return false;
1719 }
1720
1721 //reset configuration service
1722 memset(&imuconfig.ethservice.configuration, 0, sizeof(imuconfig.ethservice.configuration));
1723
1724 //set type of service
1725 imuconfig.ethservice.configuration.type = eomn_serv_AS_inertials3;
1726
1727
1728 //get acquisition rate
1730
1731 //get enabled sensor and fill canboard array. Note that we get only the enabled sensor, not all configured sensors !!!
1732
1733 imuconfig.inertials.resize(0);
1734
1735 eOas_inertial3_setof_boardinfos_t * boardInfoSet_ptr = &imuconfig.ethservice.configuration.data.as.inertial3.setofboardinfos;
1736 eOresult_t res = eoas_inertial3_setof_boardinfos_clear(boardInfoSet_ptr);
1737 if(res != eores_OK)
1738 {
1739 yError() << "ServiceParser::parseService(IMU). Error in eoas_inertial3_setof_boardinfos_clear()";
1740 return false;
1741 }
1742
1743 EOarray* array = eo_array_New(eOas_inertials3_descriptors_maxnumber, sizeof(eOas_inertial3_descriptor_t), &imuconfig.ethservice.configuration.data.as.inertial3.arrayofdescriptor);
1744 for(size_t i=0; i<as_service.settings.enabledsensors.size(); i++)
1745 {
1747 eOas_sensor_t type = sensor.type;
1748
1749 //TODO: temperature???
1750 if( (eoas_imu_acc != type) && (eoas_imu_mag != type) && (eoas_imu_gyr != type) && (eoas_imu_eul != type) &&
1751 (eoas_imu_qua != type) && (eoas_imu_lia != type) && (eoas_imu_grv != type) && (eoas_imu_status != type) &&
1752 (eoas_accel_mtb_int != type) && (eoas_accel_mtb_ext != type) && (eoas_gyros_mtb_ext != type) &&
1753 (eoas_gyros_st_l3g4200d != type))
1754 {
1755 yWarning() << "ServiceParser::parseService() has detected a wrong inertial sensor:" << eoas_sensor2string(type) << " ... we drop it";
1756 continue;
1757 }
1758 // if ok, i copy it inside ...
1759
1760 eOas_inertial3_descriptor_t des = {};
1761 des.typeofsensor = type;
1762 memcpy(&des.on, &sensor.location, sizeof(eObrd_location_t));
1763
1764 const eObrd_info_t *boardInfo_ptr = eoas_inertial3_setof_boardinfos_find(boardInfoSet_ptr, eoboards_type2cantype(sensor.boardtype));
1765 if(nullptr == boardInfo_ptr && sensor.boardtype != eobrd_ems4) // If the sensor is an ems, it does not make sense to find it in can boards
1766 //if I did not already insert the borad info with type == sensor.boardtype, now I insert it
1767 {
1768 // first of all I need to find the board info for this board type
1769 bool found = false;
1770 size_t b = 0;
1771 for(b=0; b<as_service.properties.canboards.size(); b++)
1772 {
1773 if(as_service.properties.canboards.at(b).type == eoboards_type2cantype(sensor.boardtype))
1774 {
1775 found = true;
1776 break;
1777 }
1778 }
1779 if(!found)
1780 {
1781 yError() << "ServiceParser::parseService(IMU). The sensor " << sensor.boardtype << "with type "<< eoas_sensor2string(static_cast<eOas_sensor_t> (des.typeofsensor)) << "has borad type " << eoboards_type2string2(sensor.boardtype, false) << " that is not declared in the SERVICE.PROPERTIES.CANBOARDS tag";
1782 return false;
1783 }
1784 eObrd_info_t boardInfo = {};
1785 boardInfo.type = as_service.properties.canboards.at(b).type;
1786 memcpy(&boardInfo.protocol , &as_service.properties.canboards.at(b).protocol, sizeof(eObrd_protocolversion_t));
1787 memcpy(&boardInfo.firmware, &as_service.properties.canboards.at(b).firmware, sizeof(eObrd_firmwareversion_t));
1788 res = eoas_inertial3_setof_boardinfos_add(boardInfoSet_ptr, &boardInfo);
1789 if(eores_OK != res)
1790 {
1791 yError() << "ServiceParser::parseService(IMU). Error in eoas_inertial3_setof_boardinfos_add()";
1792 return false;
1793 }
1794 }
1795 des.typeofboard = sensor.boardtype;
1796
1797 eo_array_PushBack(array, &des);
1798 imuconfig.inertials.push_back(des);
1799 imuconfig.id.push_back(sensor.id);
1800 imuconfig.sensorName.push_back(sensor.sensorName);
1801 }
1802
1803
1804 return true;
1805}
1806
1807
1808bool ServiceParser::parseService(Searchable &config, servConfigSkin_t &skinconfig)
1809{
1810
1811 skinconfig.canboard.type = eobrd_cantype_mtb;
1812 skinconfig.canboard.firmware.major = 0;
1813 skinconfig.canboard.firmware.minor = 0;
1814 skinconfig.canboard.firmware.build = 0;
1815 skinconfig.canboard.protocol.major = 0;
1816 skinconfig.canboard.protocol.minor = 0;
1817
1818
1819 if(false == check_skin(config))
1820 {
1821 yWarning() << "ServiceParser::parseService(SKIN) has received an invalid SERVICE group: using defaults";
1822 return true;
1823 }
1824
1825
1826 //check the type of board. it must be mtb / mtb4 / mtb4c / psc
1827
1828 if((eobrd_cantype_mtb != sk_service.properties.canboard.type) && (eobrd_cantype_mtb4 != sk_service.properties.canboard.type) && (eobrd_cantype_psc != sk_service.properties.canboard.type) && (eobrd_cantype_mtb4c != sk_service.properties.canboard.type))
1829 {
1830 yError() << "ServiceParser::parseService(SK): only mtb / mtb4 / mtb4c / psc boards are allowed: using defaults";
1831 return false;
1832 }
1833
1834
1835 // fill canboard
1837 skinconfig.canboard.firmware.major = sk_service.properties.canboard.firmware.major;
1838 skinconfig.canboard.firmware.minor = sk_service.properties.canboard.firmware.minor;
1839 skinconfig.canboard.firmware.build = sk_service.properties.canboard.firmware.build;
1840 skinconfig.canboard.protocol.major = sk_service.properties.canboard.protocol.major;
1841 skinconfig.canboard.protocol.minor = sk_service.properties.canboard.protocol.minor;
1842
1843 return true;
1844}
1845
1846
1847bool ServiceParser::parseService(Searchable &config, servConfigPSC_t &pscconfig)
1848{
1849 if(false == check_analog(config, eomn_serv_AS_psc))
1850 {
1851 yError() << "ServiceParser::parseService(PSC) has received an invalid SERVICE group for PSC";
1852 return false;
1853 }
1854
1855
1856 //check the num of type of boards. At max we have 1 board type
1857
1858 if(as_service.properties.canboards.size() > 1)
1859 {
1860 yError() << "ServiceParser::parseService(PSC): too many type board info are configured. The max num is " << 1;
1861 return false;
1862 }
1863
1864 if(as_service.settings.enabledsensors.size() > eOas_psc_boards_maxnumber)
1865 {
1866 yError() << "ServiceParser::parseService(PSC): too many enabled sensors are configured. The max num is " << eOas_psc_boards_maxnumber;
1867 return false;
1868 }
1869
1870 //reset configuration service
1871 memset(&pscconfig.ethservice.configuration, 0, sizeof(pscconfig.ethservice.configuration));
1872
1873 //set type of service
1874 pscconfig.ethservice.configuration.type = eomn_serv_AS_psc;
1875
1876
1877 //get acquisition rate
1879
1880 servCanBoard_t *asServBoardInfo_ptr = &as_service.properties.canboards[0];
1881 eOmn_serv_config_data_as_psc_t *pscBoardConfig_ptr = &pscconfig.ethservice.configuration.data.as.psc;
1882
1883 //get firmware and protocol info
1884 pscBoardConfig_ptr->version.firmware.major = asServBoardInfo_ptr->firmware.major;
1885 pscBoardConfig_ptr->version.firmware.minor = asServBoardInfo_ptr->firmware.minor;
1886 pscBoardConfig_ptr->version.firmware.build = asServBoardInfo_ptr->firmware.build;
1887 pscBoardConfig_ptr->version.protocol.major = asServBoardInfo_ptr->protocol.major;
1888 pscBoardConfig_ptr->version.protocol.minor = asServBoardInfo_ptr->protocol.minor;
1889
1890 for(size_t i=0; i<as_service.settings.enabledsensors.size(); i++)
1891 {
1893
1894 if(eoas_psc_angle != sensor.type)
1895 {
1896 yWarning() << "ServiceParser::parseService() has detected a wrong psc sensor:" << eoas_sensor2string(sensor.type) << " ... we drop it";
1897 continue;
1898 }
1899
1900 // if ok, i copy it inside ...
1901 pscBoardConfig_ptr->boardInfo.canloc[i].addr= sensor.location.can.addr;
1902 pscBoardConfig_ptr->boardInfo.canloc[i].port= sensor.location.can.port;
1903
1904 }
1905
1906 return true;
1907}
1908
1909
1910bool ServiceParser::parseService(Searchable &config, servConfigPOS_t &posconfig)
1911{
1912 if(false == check_analog(config, eomn_serv_AS_pos))
1913 {
1914 yError() << "ServiceParser::parseService(POS) has received an invalid SERVICE group for POS";
1915 return false;
1916 }
1917
1918
1919 if(as_service.settings.enabledsensors.size() > eOas_pos_sensorsinboard_maxnumber)
1920 {
1921 yError() << "ServiceParser::parseService(POS): too many enabled sensors are configured. The max num is " << eOas_pos_sensorsinboard_maxnumber;
1922 return false;
1923 }
1924
1925 // check that the enabledsensors have a board type which is the same for all of them and on the same location
1926
1927 eObrd_type_t boardtype = eobrd_none;
1928 eObrd_location_t location = {};
1929 for(size_t i=0; i<as_service.settings.enabledsensors.size(); i++)
1930 {
1931 if(eobrd_none == boardtype)
1932 {
1933 boardtype = as_service.settings.enabledsensors[i].boardtype;
1934 location = as_service.settings.enabledsensors[i].location;
1935 bool validBoardForPOS = (eobrd_mtb4 == boardtype) || (eobrd_mtb4c == boardtype) || (eobrd_pmc == boardtype);
1936 if(validBoardForPOS)
1937 {
1938 // ok
1939 }
1940 else
1941 {
1942 yError() << "ServiceParser::parseService(POS): sensors must have the correct boardtype (mtb4, mtb4c or pmc).";
1943 return false;
1944 }
1945
1946 }
1947
1948 if(boardtype != as_service.settings.enabledsensors[i].boardtype)
1949 {
1950 yError() << "ServiceParser::parseService(POS): all sensors must have the same boardtype. See SENSORS::boardType values";
1951 return false;
1952 }
1953
1954 if((location.can.port != as_service.settings.enabledsensors[i].location.can.port) || (location.can.addr != as_service.settings.enabledsensors[i].location.can.addr))
1955 {
1956 yError() << "ServiceParser::parseService(POS): all sensors must have the same can location. See SENSORS::location values";
1957 return false;
1958 }
1959 }
1960
1961 // look for the boardtype inside the as_service.properties.canboards
1962 servCanBoard_t *board = nullptr;
1963 for(size_t i=0; i<as_service.properties.canboards.size(); i++)
1964 {
1965 if(static_cast<eObrd_cantype_t>(boardtype) == as_service.properties.canboards[i].type)
1966 {
1968 }
1969 }
1970
1971 if(nullptr == board)
1972 {
1973 yError() << "ServiceParser::parseService(POS): cannot find the boardtype " << eoboards_type2string2(boardtype, eobool_true) << " of SENSORS::boardType inside CANBOARDS::type";
1974 return false;
1975 }
1976
1977 // reset configuration service
1978 memset(&posconfig.ethservice.configuration, 0, sizeof(posconfig.ethservice.configuration));
1979
1980 // set type of service
1981 posconfig.ethservice.configuration.type = eomn_serv_AS_pos;
1982
1983
1984 //get acquisition rate
1986
1987
1988 // get firmware and protocol info
1989 eOmn_serv_config_data_as_pos_t *pos = &posconfig.ethservice.configuration.data.as.pos;
1990 for(size_t b=0; b<eOas_pos_boards_maxnumber; b++)
1991 {
1992 pos->config.boardconfig[b].boardinfo.type = boardtype;
1993 pos->config.boardconfig[b].boardinfo.firmware.major = board->firmware.major;
1994 pos->config.boardconfig[b].boardinfo.firmware.minor = board->firmware.minor;
1995 pos->config.boardconfig[b].boardinfo.firmware.build = board->firmware.build;
1996 pos->config.boardconfig[b].boardinfo.protocol.major = board->protocol.major;
1997 pos->config.boardconfig[b].boardinfo.protocol.minor = board->protocol.minor;
1998
1999 pos->config.boardconfig[b].canloc.addr = location.can.addr;
2000 pos->config.boardconfig[b].canloc.port = location.can.port;
2001
2002 for(size_t s=0; s<as_service.settings.enabledsensors.size(); s++)
2003 {
2005 pos->config.boardconfig[b].sensors[s].connector = snsr.pos.connector;
2006 pos->config.boardconfig[b].sensors[s].type = snsr.pos.calibration.type;
2007 pos->config.boardconfig[b].sensors[s].port = snsr.pos.port;
2008 pos->config.boardconfig[b].sensors[s].enabled = 1;
2009 pos->config.boardconfig[b].sensors[s].invertdirection = snsr.pos.calibration.invertdirection;
2010 pos->config.boardconfig[b].sensors[s].rotation = snsr.pos.calibration.rotation;
2011 pos->config.boardconfig[b].sensors[s].offset = static_cast<int16_t>(10 * snsr.pos.calibration.offset);
2012 }
2013
2014 }
2015
2016 return true;
2017}
2018
2019#if defined(SERVICE_PARSER_USE_MC)
2020
2021
2022bool ServiceParser::parse_encoder_port(std::string const &fromstring, eObrd_ethtype_t const ethboard, eOmc_encoder_t type, uint8_t &toport, bool &formaterror)
2023{
2024 const char *t = fromstring.c_str();
2025 bool ret = false;
2026 switch(type)
2027 {
2028 case eomc_enc_unknown:
2029 {
2030 yWarning() << "ServiceParser::parse_encoder_port():" << t << "cannot be converted into a port because argument type is" << eomc_encoder2string(type, eobool_false);
2031 toport = eobrd_port_none;
2032 ret = false;
2033 } break;
2034
2035
2036 case eomc_enc_none:
2037 {
2038 toport = eobrd_port_none;
2039 ret = true;
2040 } break;
2041
2042 case eomc_enc_aea:
2043 case eomc_enc_aea3:
2044 case eomc_enc_aksim2:
2045 case eomc_enc_amo:
2046 case eomc_enc_qenc:
2047 case eomc_enc_spichainof2:
2048 case eomc_enc_absanalog:
2049 case eomc_enc_spichainof3:
2050 {
2051 uint8_t toport1 = eobrd_port_unknown;
2052 bool result = parse_port_conn(fromstring, static_cast<eObrd_type_t>(ethboard), toport1, formaterror);
2053
2054 if(false == result)
2055 {
2056 yWarning() << "ServiceParser::parse_encoder_port():" << t << "is not a legal string for an encoder connector port";
2057 formaterror = true;
2058 ret = false;
2059 }
2060 else
2061 {
2062 toport = toport1;
2063 ret = true;
2064 }
2065
2066 } break;
2067
2068
2069 case eomc_enc_mais:
2070 {
2071 uint8_t toport1 = eobrd_port_unknown;
2072 bool result = parse_port_mais(fromstring, toport1, formaterror);
2073
2074 if(false == result)
2075 {
2076 yWarning() << "ServiceParser::parse_encoder_port():" << t << "is not a legal string for an encoder connector port";
2077 formaterror = true;
2078 ret = false;
2079 }
2080 else
2081 {
2082 toport = toport1;
2083 ret = true;
2084 }
2085
2086 } break;
2087
2088 case eomc_enc_psc:
2089 {
2090 uint8_t toport1 = eobrd_port_unknown;
2091 bool result = parse_port_psc(fromstring, toport1, formaterror);
2092
2093 if(false == result)
2094 {
2095 yWarning() << "ServiceParser::parse_encoder_port():" << t << "is not a legal string for an encoder connector port";
2096 formaterror = true;
2097 ret = false;
2098 }
2099 else
2100 {
2101 toport = toport1;
2102 ret = true;
2103 }
2104
2105 } break;
2106
2107 case eomc_enc_pos:
2108 {
2109 uint8_t toport1 = eobrd_port_unknown;
2110 bool result = parse_port_pos(fromstring, toport1, formaterror);
2111
2112 if(false == result)
2113 {
2114 yWarning() << "ServiceParser::parse_encoder_port():" << t << "is not a legal string for an encoder connector port";
2115 formaterror = true;
2116 ret = false;
2117 }
2118 else
2119 {
2120 toport = toport1;
2121 ret = true;
2122 }
2123
2124 } break;
2125
2126 default:
2127 {
2128 int len = strlen(t);
2129
2130 if(len > 15)
2131 {
2132 yWarning() << "ServiceParser::parse_encoder_port():" << t << "is not a legal string for a encoder port because it is too long with size =" << len;
2133 formaterror = true;
2134 return false;
2135 }
2136 char prefix[16] = {0};
2137 sscanf(t, "%3c", prefix);
2138 if(0 == strcmp(prefix, "CAN"))
2139 {
2140 toport = eobrd_port_nolocal;
2141 ret = true;
2142 }
2143 else
2144 {
2145 toport = eobrd_port_none;
2146 yWarning() << "ServiceParser::parse_encoder_port():" << t << "is not a legal string for a encoder port!";
2147 formaterror = true;
2148 return false;
2149 }
2150 }break;
2151 }
2152 return ret;
2153}
2154
2155
2156bool ServiceParser::parse_port_conn(std::string const &fromstring, eObrd_type_t const board, uint8_t &toport, bool &formaterror)
2157{
2158 const char *t = fromstring.c_str();
2159 bool ret = false;
2160
2161 // format of string is CONN:P4 or CONN:eobrd_conn_P4 ... the parse function verifies presence of CONN:
2162 eObrd_connector_t conn = eobrd_conn_unknown;
2163 bool result = parse_connector(fromstring, conn, formaterror);
2164
2165 if(false == result)
2166 {
2167 yWarning() << "ServiceParser::parse_port_conn():" << t << "is not a legal string for a eObrd_connector_t";
2168 formaterror = true;
2169 ret = false;
2170 }
2171 else
2172 {
2173 eObrd_port_t port = eoboards_connector2port(conn, board);
2174 if(eobrd_port_unknown == port)
2175 {
2176 yWarning() << "ServiceParser::parse_port_conn():" << t << "does not convert to a legal port for connector" << eoboards_connector2string(conn, eobool_false) << "and parsed board";
2177 formaterror = true;
2178 ret = false;
2179 }
2180 else
2181 {
2182 toport = port;
2183 ret = true;
2184 }
2185 }
2186
2187 return ret;
2188}
2189
2190
2191
2192bool ServiceParser::parse_port_mais(std::string const &fromstring, uint8_t &toport, bool &formaterror)
2193{
2194 const char *t = fromstring.c_str();
2195 bool ret = false;
2196
2197 // format of string is MAIS:eobrd_portmais_thumbproximal or MAIS:thumbproximal
2198 eObrd_portmais_t pmais = eobrd_portmais_unknown;
2199 bool result = parse_mais(fromstring, pmais, formaterror);
2200
2201 if(false == result)
2202 {
2203 yWarning() << "ServiceParser::parse_port_mais():" << t << "is not a legal string for a port mais";
2204 formaterror = true;
2205 ret = false;
2206 }
2207 else
2208 {
2209 toport = pmais;
2210 ret = true;
2211 }
2212
2213 return ret;
2214}
2215
2216
2217bool ServiceParser::parse_port_psc(std::string const &fromstring, uint8_t &toport, bool &formaterror)
2218{
2219 const char *t = fromstring.c_str();
2220 bool ret = false;
2221
2222 // format of string is PSC:finger0 or finger0
2223 eObrd_portpsc_t ppsc = eobrd_portpsc_unknown;
2224 bool result = parse_psc(fromstring, ppsc, formaterror);
2225
2226 if(false == result)
2227 {
2228 yWarning() << "ServiceParser::parse_port_psc():" << t << "is not a legal string for a port psc";
2229 formaterror = true;
2230 ret = false;
2231 }
2232 else
2233 {
2234 toport = ppsc;
2235 ret = true;
2236 }
2237
2238 return ret;
2239}
2240
2241
2242bool ServiceParser::parse_port_pos(std::string const &fromstring, uint8_t &toport, bool &formaterror)
2243{
2244// const char *t = fromstring.c_str();
2245 bool ret = false;
2246
2247 // format of string is POS:hand_thumb or :hand_index or :hand_medium or :hand_pinky
2248 eObrd_portpos_t ppos = eobrd_portpos_unknown;
2249 bool result = parse_POS_port(fromstring, ppos, formaterror);
2250
2251 if(false == result)
2252 {
2253 yWarning() << "ServiceParser::parse_port_pos():" << fromstring << "is not a legal string for a port pos";
2254 formaterror = true;
2255 ret = false;
2256 }
2257 else
2258 {
2259 toport = ppos;
2260 ret = true;
2261 }
2262
2263 return ret;
2264}
2265
2266
2267
2268
2269//bool ServiceParser::parse_mais(std::string const &fromstring, eObrd_portmais_t &pmais, bool &formaterror)
2270//{
2271// // parses MAIS:eobrd_portmais_thumbproximal or MAIS:thumbproximal
2272
2273// const char *tt = fromstring.c_str();
2274// char prefix[16] = {0};
2275// sscanf(tt, "%5c", prefix);
2276
2277// if(0 != strcmp(prefix, "MAIS:"))
2278// {
2279// yWarning() << "ServiceParser::parse_mais():" << tt << "is not a legal string because it must begin with MAIS:";
2280// formaterror = true;
2281// return false;
2282// }
2283
2284// // ok, now i remove the first 5 characters "MAIS:" and parse the second section .... it can be extended or compact
2285// const char *t = &tt[5];
2286
2287// eObool_t usecompactstring = eobool_false;
2288// pmais = eoboards_string2portmais(t, usecompactstring);
2289
2290// if(eobrd_portmais_unknown == pmais)
2291// { // attempting to retrieve the compact form
2292// usecompactstring = eobool_true;
2293// pmais = eoboards_string2portmais(t, usecompactstring);
2294// }
2295
2296// if(eobrd_portmais_unknown == pmais)
2297// {
2298// yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eObrd_portmais_t";
2299// formaterror = true;
2300// return false;
2301// }
2302
2303// return true;
2304
2305//}
2306
2307
2308// we want to fill the des with relevant info:
2309// we may have CAN1:1:0 if we have a act_foc or an act_mc4, or a CONN:P4 if we have a pwm.
2310// hence, we need ... the string, the type of actuator, the ethboard (for transforming P4 into teh proper port value.
2311bool ServiceParser::parse_actuator_port(std::string const &fromstring, eObrd_ethtype_t const ethboard, eOmc_actuator_t const type, eOmc_actuator_descriptor_t &todes, bool &formaterror)
2312{
2313 const char *t = fromstring.c_str();
2314
2315 bool ret = false;
2316 switch(type)
2317 {
2318 default:
2319 case eomc_act_unknown:
2320 {
2321 yWarning() << "ServiceParser::parse_actuator_port():" << t << "cannot be converted into a eObrd_location_t because argument type is" << eomc_actuator2string(type, eobool_false);
2322 todes.none.port = eobrd_port_none;
2323 ret = false;
2324 } break;
2325
2326
2327 case eomc_act_none:
2328 {
2329 //yWarning() << "ServiceParser::parse_actuator_port():" << t << "cannot be converted into a eObrd_location_t because argument type is" << eomc_actuator2string(type);
2330 todes.none.port = eobrd_port_none;
2331 ret = true;
2332 } break;
2333
2334 case eomc_act_pwm:
2335 {
2336
2337 uint8_t toport = eobrd_port_unknown;
2338 bool result = parse_port_conn(fromstring, static_cast<eObrd_type_t>(ethboard), toport, formaterror);
2339
2340 if(false == result)
2341 {
2342 yWarning() << "ServiceParser::parse_actuator_port():" << t << "is not a legal string for a pwm connector port";
2343 formaterror = true;
2344 ret = false;
2345 }
2346 else
2347 {
2348 todes.pwm.port = toport;
2349 ret = true;
2350 }
2351
2352 } break;
2353
2354 case eomc_act_foc:
2355 case eomc_act_mc4:
2356 {
2357 // read it as a CAN address
2358 eObrd_location_t loc;
2359 bool result = convert(fromstring, loc, formaterror);
2360 ret = true;
2361 if(false == result)
2362 {
2363 yWarning() << "ServiceParser::parse_actuator_port():" << t << "is not a legal string for a eObrd_location_t";
2364 formaterror = true;
2365 ret = false;
2366 }
2367 else if((eomc_act_mc4 == type) && (eobrd_place_extcan != loc.any.place))
2368 {
2369 yWarning() << "ServiceParser::parse_actuator_port():" << t << "is not a legal string for a eomc_act_mc4 location because it is not a eobrd_place_extcan";
2370 formaterror = true;
2371 ret = false;
2372 }
2373 else if(eomc_act_foc == type)
2374 {
2375 if((eobrd_place_can != loc.any.place) && (eobrd_place_extcan != loc.any.place))
2376 {
2377 yWarning() << "ServiceParser::parse_actuator_port():" << t << "is not a legal string for a eomc_act_foc location because it is not a eobrd_place_extcan or eobrd_place_can";
2378 formaterror = true;
2379 ret = false;
2380 }
2381 }
2382
2383 if(false == ret)
2384 {
2385 return ret;
2386 }
2387
2388 if(eomc_act_foc == type)
2389 {
2390 // copy into todes.foc
2391 if(eobrd_place_can == loc.any.place)
2392 {
2393 todes.foc.canloc.port = loc.can.port;
2394 todes.foc.canloc.addr = loc.can.addr;
2395 todes.foc.canloc.insideindex = eobrd_caninsideindex_first;
2396
2397 ret = true;
2398 }
2399 else
2400 {
2401 todes.foc.canloc.port = loc.extcan.port;
2402 todes.foc.canloc.addr = loc.extcan.addr;
2403 todes.foc.canloc.insideindex = loc.extcan.index;
2404 if(eobrd_caninsideindex_first != todes.foc.canloc.insideindex)
2405 {
2406 yWarning() << "ServiceParser::parse_actuator_port():" << "in eomc_act_foc the location has an index different from eobrd_caninsideindex_first. For now we force to it, but correct xml file.";
2407 todes.foc.canloc.insideindex = eobrd_caninsideindex_first;
2408 ret = true;
2409 }
2410 else
2411 {
2412 ret = true;
2413 }
2414 }
2415
2416 }
2417 else if(eomc_act_mc4 == type)
2418 {
2419 // copy into todes.mc4
2420 todes.mc4.canloc.port = loc.extcan.port;
2421 todes.mc4.canloc.addr = loc.extcan.addr;
2422 todes.mc4.canloc.insideindex = loc.extcan.index;
2423
2424 if(eobrd_caninsideindex_none == todes.foc.canloc.insideindex)
2425 {
2426 yWarning() << "ServiceParser::parse_actuator_port():" << "in eomc_act_mc4 the location has an eobrd_caninsideindex_none. Correct xml file.";
2427 formaterror = true;
2428 ret = false;
2429 }
2430 else
2431 {
2432 ret = true;
2433 }
2434 }
2435
2436 } break;
2437
2438 case eomc_act_advfoc:
2439 {
2440 // read it as a location
2441 eOlocation_t loc {eobus_none, 0, 0};
2442 bool result = convert(fromstring, loc, formaterror);
2443 ret = true;
2444 if(false == result)
2445 {
2446 yWarning() << "ServiceParser::parse_actuator_port():" << t << "is not a legal string for a eOlocation_t required by eomc_act_advfoc";
2447 formaterror = true;
2448 ret = false;
2449 }
2450
2451 if(false == ret)
2452 {
2453 return ret;
2454 }
2455
2456 // copy into todes.gen as it is uded by advfoc
2457 todes.gen.location = loc;
2458
2459 } break;
2460
2461
2462 }
2463
2464 return ret;
2465}
2466
2467
2468bool ServiceParser::convert(std::string const &fromstring, eOmc_actuator_t &toactuatortype, bool &formaterror)
2469{
2470 const char *t = fromstring.c_str();
2471 eObool_t usecompactstring = eobool_false;
2472 toactuatortype = eomc_string2actuator(t, usecompactstring);
2473
2474 if(eomc_act_unknown == toactuatortype)
2475 { // attempting to retrieve the compact form
2476 usecompactstring = eobool_true;
2477 toactuatortype = eomc_string2actuator(t, usecompactstring);
2478 }
2479
2480 if(eomc_act_unknown == toactuatortype)
2481 {
2482 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOmc_actuator_t";
2483 formaterror = true;
2484 return false;
2485 }
2486
2487 return true;
2488}
2489
2490
2491bool ServiceParser::convert(std::string const &fromstring, eOmc_position_t &toposition, bool &formaterror)
2492{
2493 const char *t = fromstring.c_str();
2494 eObool_t usecompactstring = eobool_false;
2495 toposition = eomc_string2position(t, usecompactstring);
2496
2497 if(eomc_pos_unknown == toposition)
2498 { // attempting to retrieve the compact form
2499 usecompactstring = eobool_true;
2500 toposition = eomc_string2position(t, usecompactstring);
2501 }
2502
2503 if(eomc_pos_unknown == toposition)
2504 {
2505 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOmc_position_t";
2506 formaterror = true;
2507 return false;
2508 }
2509
2510 return true;
2511}
2512
2513bool ServiceParser::parse_connector(const std::string &fromstring, eObrd_connector_t &toconnector, bool &formaterror)
2514{
2515 // parses CONN:P4 or CONN:eobrd_conn_P4
2516
2517 const char *tt = fromstring.c_str();
2518 char prefix[16] = {0};
2519 sscanf(tt, "%5c", prefix);
2520
2521 if(0 != strcmp(prefix, "CONN:"))
2522 {
2523 yWarning() << "ServiceParser::convert():" << tt << "is not a legal string for eObrd_connector_t because it must begin with CONN:";
2524 formaterror = true;
2525 return false;
2526 }
2527
2528 // ok, now i remove the first 5 characters "CONN:" and parse the second section .... it can be extended or compact
2529 const char *t = &tt[5];
2530
2531 eObool_t usecompactstring = eobool_false;
2532 toconnector = eoboards_string2connector(t, usecompactstring);
2533
2534 if(eobrd_conn_unknown == toconnector)
2535 { // attempting to retrieve the compact form
2536 usecompactstring = eobool_true;
2537 toconnector = eoboards_string2connector(t, usecompactstring);
2538 }
2539
2540 if(eobrd_conn_unknown == toconnector)
2541 {
2542 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eObrd_connector_t";
2543 formaterror = true;
2544 return false;
2545 }
2546
2547 return true;
2548}
2549
2550bool ServiceParser::parse_mais(const std::string &fromstring, eObrd_portmais_t &toportmais, bool &formaterror)
2551{
2552 // parses MAIS:eobrd_portmais_thumbproximal or MAIS:thumbproximal
2553
2554 const char *tt = fromstring.c_str();
2555 char prefix[16] = {0};
2556 sscanf(tt, "%5c", prefix);
2557
2558 if(0 != strcmp(prefix, "MAIS:"))
2559 {
2560 yWarning() << "ServiceParser::parse_mais():" << tt << "is not a legal string for eObrd_portmais_t because it must begin with MAIS:";
2561 formaterror = true;
2562 return false;
2563 }
2564
2565 // ok, now i remove the first 5 characters "MAIS:" and parse the second section .... it can be extended or compact
2566 const char *t = &tt[5];
2567
2568 eObool_t usecompactstring = eobool_false;
2569 toportmais = eoboards_string2portmais(t, usecompactstring);
2570
2571 if(eobrd_portmais_unknown == toportmais)
2572 { // attempting to retrieve the compact form
2573 usecompactstring = eobool_true;
2574 toportmais = eoboards_string2portmais(t, usecompactstring);
2575 }
2576
2577 if(eobrd_portmais_unknown == toportmais)
2578 {
2579 yWarning() << "ServiceParser::parse_mais():" << t << "is not a legal string for eObrd_portmais_t";
2580 formaterror = true;
2581 return false;
2582 }
2583
2584 return true;
2585}
2586
2587
2588bool ServiceParser::parse_psc(const std::string &fromstring, eObrd_portpsc_t &toportpsc, bool &formaterror)
2589{
2590 // parses PSC:finger0 or finger0
2591
2592 const char *tt = fromstring.c_str();
2593 char prefix[16] = {0};
2594 sscanf(tt, "%4c", prefix);
2595
2596 const char *t=nullptr;
2597
2598 if(0 != strcmp(prefix, "PSC:"))
2599 t = &tt[0]; // port of type finger0
2600 else
2601 t = &tt[4]; // port of type PSC:finger0
2602
2603 eObool_t usecompactstring = eobool_false;
2604 toportpsc = eoboards_string2portpsc(t, usecompactstring);
2605
2606 if(eobrd_portpsc_unknown == toportpsc)
2607 { // attempting to retrieve the compact form
2608 usecompactstring = eobool_true;
2609 toportpsc = eoboards_string2portpsc(t, usecompactstring);
2610 }
2611
2612 if(eobrd_portpsc_unknown == toportpsc)
2613 {
2614 yWarning() << "ServiceParser::parse_psc(): " << t << " is not a legal string for eObrd_portpsc_t";
2615 formaterror = true;
2616 return false;
2617 }
2618
2619 return true;
2620}
2621
2622bool ServiceParser::parse_POS_port(const std::string &fromstring, eObrd_portpos_t &toportpos, bool &formaterror)
2623{
2624 // parses POS:hand_thumb or :hand_index or :hand_medium or :hand_pinky
2625
2626 const char *tt = fromstring.c_str();
2627 char prefix[16] = {0};
2628 sscanf(tt, "%4c", prefix);
2629
2630 const char *t=nullptr;
2631
2632 if(0 != strcmp(prefix, "POS:"))
2633 t = &tt[0]; // port of type hand_thumb
2634 else
2635 t = &tt[4]; // port of type POS:hand_thumb
2636
2637 eObool_t usecompactstring = eobool_false;
2638 toportpos = eoboards_string2portpos(t, usecompactstring);
2639
2640 if(eobrd_portpos_unknown == toportpos)
2641 { // attempting to retrieve the compact form
2642 usecompactstring = eobool_true;
2643 toportpos = eoboards_string2portpos(t, usecompactstring);
2644 }
2645
2646 if(eobrd_portpos_unknown == toportpos)
2647 {
2648 yWarning() << "ServiceParser::parse_POS_port(): " << t << " is not a legal string for eObrd_portpos_t";
2649 formaterror = true;
2650 return false;
2651 }
2652
2653 return true;
2654}
2655
2656
2657
2658bool ServiceParser::parse_POS_CALIB_type(std::string const &fromstring, eoas_pos_TYPE_t &type, bool &formaterror)
2659{
2660 const char *tt = fromstring.c_str();
2661 char prefix[16] = {0};
2662 sscanf(tt, "%5c", prefix);
2663
2664 if(0 != strcmp(prefix, "TYPE:"))
2665 {
2666 yWarning() << "ServiceParser::convert():" << tt << "is not a legal string for eoas_pos_TYPE_t because it must begin with TYPE:";
2667 formaterror = true;
2668 return false;
2669 }
2670
2671 // ok, now i remove the first 5 characters "TYPE:" and parse the second section .... it can be extended or compact
2672 const char *t = &tt[5];
2673
2674 eObool_t usecompactstring = eobool_false;
2675 type = eoas_string2postype(t, usecompactstring);
2676
2677 if(eoas_pos_TYPE_unknown == type)
2678 { // attempting to retrieve the compact form
2679 usecompactstring = eobool_true;
2680 type = eoas_string2postype(t, usecompactstring);
2681 }
2682
2683 if(eoas_pos_TYPE_unknown == type)
2684 {
2685 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eoas_pos_TYPE_t";
2686 formaterror = true;
2687 return false;
2688 }
2689
2690 return true;
2691}
2692
2693bool ServiceParser::parse_POS_CALIB_rotation(std::string const &fromstring, eoas_pos_ROT_t &rot, bool &formaterror)
2694{
2695 const char *tt = fromstring.c_str();
2696 char prefix[16] = {0};
2697 sscanf(tt, "%4c", prefix);
2698
2699 if(0 != strcmp(prefix, "ROT:"))
2700 {
2701 yWarning() << "ServiceParser::convert():" << tt << "is not a legal string for eoas_pos_ROT_t because it must begin with ROT:";
2702 formaterror = true;
2703 return false;
2704 }
2705
2706 // ok, now i remove the first 4 characters "ROT:" and parse the second section .... it can be extended or compact
2707 const char *t = &tt[4];
2708
2709 eObool_t usecompactstring = eobool_false;
2710 rot = eoas_string2posrot(t, usecompactstring);
2711
2712 yDebug() << t << " yyyyyyyyyyyyyyyyyyy " << rot;
2713
2714
2715 if(eoas_pos_ROT_unknown == rot)
2716 { // attempting to retrieve the compact form
2717 usecompactstring = eobool_true;
2718 rot = eoas_string2posrot(t, usecompactstring);
2719 yDebug() << t << " xxxxxxxxxxxxxxxxxxx " << rot;
2720 }
2721
2722 if(eoas_pos_ROT_unknown == rot)
2723 {
2724 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eoas_pos_ROT_t";
2725 formaterror = true;
2726 return false;
2727 }
2728
2729 return true;
2730}
2731
2732bool ServiceParser::parse_POS_connector(std::string const &fromstring, const eObrd_type_t brd, eObrd_connector_t &conn, bool &formaterror)
2733{
2734 uint8_t tmp {0};
2735 bool r = parse_port_conn(fromstring, brd, tmp, formaterror);
2736 conn = r ? static_cast<eObrd_connector_t>(tmp) : eobrd_conn_unknown;
2737 return r;
2738}
2739
2740bool ServiceParser::convert(std::string const &fromstring, eOmc_encoder_t &toencodertype, bool &formaterror)
2741{
2742 const char *t = fromstring.c_str();
2743 eObool_t usecompactstring = eobool_false;
2744 toencodertype = eomc_string2encoder(t, usecompactstring);
2745
2746 if(eomc_enc_unknown == toencodertype)
2747 { // attempting to retrieve the compact form
2748 usecompactstring = eobool_true;
2749 toencodertype = eomc_string2encoder(t, usecompactstring);
2750 }
2751
2752 if(eomc_enc_unknown == toencodertype)
2753 {
2754 yWarning() << "ServiceParser::convert():" << t << "is not a legal string for eOmc_encoder_t";
2755 formaterror = true;
2756 return false;
2757 }
2758
2759 return true;
2760}
2761
2762
2763bool ServiceParser::check_motion(Searchable &config)
2764{
2765 bool formaterror = false;
2766
2767 // complete format is SERVICE{ type, PROPERTIES{ ETHBOARD, CANBOARDS, MC4, MAIS, CONTROLLER, JOINTMAPPING, JOINTSETS } }
2768 // so far, there is no SETTINGS{}.
2769 // then, some groups are not present for some kind of SERVICE.type
2770 // mc4: ETHBOARD, CANBOARDS, MC4, MAIS
2771 // foc: ETHBOARD, CANBOARDS, CONTROLLER, JOINTMAPPING, JOINTSETS
2772 // mc4plus: ETHBOARD, CONTROLLER, JOINTMAPPING, JOINTSETS
2773 // mc4plusmais: ETHBOARD, CANBOARDS, MAIS, CONTROLLER, JOINTMAPPING, JOINTSETS
2774
2775
2776
2777 const bool itisOKifwedontfindtheXMLgroup = true;
2778
2779 Bottle b_SERVICE(config.findGroup("SERVICE"));
2780 if(b_SERVICE.isNull())
2781 {
2782 if(false == itisOKifwedontfindtheXMLgroup)
2783 {
2784 yError() << "ServiceParser::check_motion() cannot find SERVICE group";
2785 return false;
2786 }
2787 else
2788 {
2789 yWarning() << "ServiceParser::check_motion() cannot find SERVICE group, but we are in permissive mode, hence we ask the ETH board to config itself according to its IP address";
2790 mc_service.type = eomn_serv_MC_generic;
2791 return true;
2792 }
2793 }
2794
2795 // check whether we have the proper type
2796
2797 if(false == b_SERVICE.check("type"))
2798 {
2799 if(false == itisOKifwedontfindtheXMLgroup)
2800 {
2801 yError() << "ServiceParser::check_motion() cannot find SERVICE.type";
2802 return false;
2803 }
2804 else
2805 {
2806 yWarning() << "ServiceParser::check_motion() cannot find SERVICE.type, but we are in permissive mode, hence we ask the ETH board to config itself according to its IP address";
2807 mc_service.type = eomn_serv_MC_generic;
2808 return true;
2809 }
2810 }
2811
2812 Bottle b_type(b_SERVICE.find("type").asString());
2813 if(false == convert(b_type.toString(), mc_service.type, formaterror))
2814 {
2815 yError() << "ServiceParser::check_motion() has found unknown SERVICE.type = " << b_type.toString();
2816 return false;
2817 }
2818
2819 if(eomn_serv_MC_generic == mc_service.type)
2820 {
2821 yWarning() << "ServiceParser::check_motion() detects SERVICE.type = eomn_serv_MC_generic.. hence we ask the ETH board to config itself according to its IP address";
2822 return true;
2823 }
2824
2825 // check whether we have the proper groups at first level.
2826
2827 Bottle b_PROPERTIES = Bottle(b_SERVICE.findGroup("PROPERTIES"));
2828 if(b_PROPERTIES.isNull())
2829 {
2830 yError() << "ServiceParser::check_motion() cannot find PROPERTIES";
2831 return false;
2832 }
2833
2834
2835 // now, inside PROPERTIES there are groups which depend on mc_service.type.
2836 // i prefer to check them all in here rather to go on and check them one after another.
2837 Bottle b_PROPERTIES_ETHBOARD = Bottle(b_PROPERTIES.findGroup("ETHBOARD"));
2838 bool has_PROPERTIES_ETHBOARD = !b_PROPERTIES_ETHBOARD.isNull();
2839
2840 Bottle b_PROPERTIES_MAIS = Bottle(b_PROPERTIES.findGroup("MAIS"));
2841 bool has_PROPERTIES_MAIS = !b_PROPERTIES_MAIS.isNull();
2842
2843 Bottle b_PROPERTIES_PSC = Bottle(b_PROPERTIES.findGroup("PSC"));
2844 bool has_PROPERTIES_PSC = !b_PROPERTIES_PSC.isNull();
2845
2846 Bottle b_PROPERTIES_POS = Bottle(b_PROPERTIES.findGroup("POS"));
2847 bool has_PROPERTIES_POS = !b_PROPERTIES_POS.isNull();
2848
2849 Bottle b_PROPERTIES_MC4 = Bottle(b_PROPERTIES.findGroup("MC4"));
2850 bool has_PROPERTIES_MC4 = !b_PROPERTIES_MC4.isNull();
2851
2852 Bottle b_PROPERTIES_CANBOARDS = Bottle(b_PROPERTIES.findGroup("CANBOARDS"));
2853 bool has_PROPERTIES_CANBOARDS = !b_PROPERTIES_CANBOARDS.isNull();
2854
2855 Bottle b_PROPERTIES_JOINTMAPPING = Bottle(b_PROPERTIES.findGroup("JOINTMAPPING"));
2856 bool has_PROPERTIES_JOINTMAPPING = !b_PROPERTIES_JOINTMAPPING.isNull();
2857
2858 Bottle b_PROPERTIES_DIAGNOSTICS = Bottle(b_PROPERTIES.findGroup("DIAGNOSTICS"));
2859 bool has_PROPERTIES_DIAGNOSTICS = !b_PROPERTIES_DIAGNOSTICS.isNull();
2860
2861
2862
2863
2864
2865 bool itisoksofar = false;
2866 switch(mc_service.type)
2867 {
2868 case eomn_serv_MC_foc:
2869 {
2870 // must have: ETHBOARD, CANBOARDS, JOINTMAPPING
2871 itisoksofar = true;
2872
2873 if(false == has_PROPERTIES_ETHBOARD)
2874 {
2875 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
2876 itisoksofar = false;
2877 }
2878
2879 if(false == has_PROPERTIES_CANBOARDS)
2880 {
2881 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS for type" << eomn_servicetype2string(mc_service.type);
2882 itisoksofar = false;
2883 }
2884
2885 if(false == has_PROPERTIES_JOINTMAPPING)
2886 {
2887 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING for type" << eomn_servicetype2string(mc_service.type);
2888 itisoksofar = false;
2889 }
2890
2891 } break;
2892
2893
2894 case eomn_serv_MC_mc4plus:
2895 {
2896 // must have: ETHBOARD, JOINTMAPPING
2897
2898 itisoksofar = true;
2899
2900 if(false == has_PROPERTIES_ETHBOARD)
2901 {
2902 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
2903 itisoksofar = false;
2904 }
2905
2906 if(false == has_PROPERTIES_JOINTMAPPING)
2907 {
2908 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING for type" << eomn_servicetype2string(mc_service.type);
2909 itisoksofar = false;
2910 }
2911
2912 } break;
2913
2914
2915 case eomn_serv_MC_mc4plusmais:
2916 {
2917 // must have: ETHBOARD, CANBOARDS, MAIS, JOINTMAPPING
2918
2919 itisoksofar = true;
2920
2921 if(false == has_PROPERTIES_ETHBOARD)
2922 {
2923 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
2924 itisoksofar = false;
2925 }
2926
2927 if(false == has_PROPERTIES_CANBOARDS)
2928 {
2929 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS for type" << eomn_servicetype2string(mc_service.type);
2930 itisoksofar = false;
2931 }
2932
2933 if(false == has_PROPERTIES_MAIS)
2934 {
2935 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MAIS for type" << eomn_servicetype2string(mc_service.type);
2936 itisoksofar = false;
2937 }
2938
2939 if(false == has_PROPERTIES_JOINTMAPPING)
2940 {
2941 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING for type" << eomn_servicetype2string(mc_service.type);
2942 itisoksofar = false;
2943 }
2944
2945
2946 } break;
2947
2948 case eomn_serv_MC_mc4:
2949 {
2950 // must have: ETHBOARD, CANBOARDS, MC4, MAIS
2951
2952 itisoksofar = true;
2953
2954 if(false == has_PROPERTIES_ETHBOARD)
2955 {
2956 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
2957 itisoksofar = false;
2958 }
2959
2960 if(false == has_PROPERTIES_CANBOARDS)
2961 {
2962 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS for type" << eomn_servicetype2string(mc_service.type);
2963 itisoksofar = false;
2964 }
2965
2966 if(false == has_PROPERTIES_MC4)
2967 {
2968 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4 for type" << eomn_servicetype2string(mc_service.type);
2969 itisoksofar = false;
2970 }
2971
2972 if(false == has_PROPERTIES_MAIS)
2973 {
2974 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MAIS for type" << eomn_servicetype2string(mc_service.type);
2975 itisoksofar = false;
2976 }
2977
2978 } break;
2979
2980 case eomn_serv_MC_mc2pluspsc:
2981 {
2982 // must have: ETHBOARD, CANBOARDS, PSC, JOINTMAPPING
2983
2984 itisoksofar = true;
2985
2986 if(false == has_PROPERTIES_ETHBOARD)
2987 {
2988 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
2989 itisoksofar = false;
2990 }
2991
2992 if(false == has_PROPERTIES_CANBOARDS)
2993 {
2994 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS for type" << eomn_servicetype2string(mc_service.type);
2995 itisoksofar = false;
2996 }
2997
2998 if(false == has_PROPERTIES_PSC)
2999 {
3000 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.PSC for type" << eomn_servicetype2string(mc_service.type);
3001 itisoksofar = false;
3002 }
3003
3004 if(false == has_PROPERTIES_JOINTMAPPING)
3005 {
3006 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING for type" << eomn_servicetype2string(mc_service.type);
3007 itisoksofar = false;
3008 }
3009
3010
3011 } break;
3012
3013
3014 case eomn_serv_MC_mc4plusfaps:
3015 {
3016 // must have: ETHBOARD, CANBOARDS, POS, JOINTMAPPING
3017
3018 itisoksofar = true;
3019
3020 if(false == has_PROPERTIES_ETHBOARD)
3021 {
3022 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
3023 itisoksofar = false;
3024 }
3025
3026 if(false == has_PROPERTIES_CANBOARDS)
3027 {
3028 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS for type" << eomn_servicetype2string(mc_service.type);
3029 itisoksofar = false;
3030 }
3031
3032 if(false == has_PROPERTIES_POS)
3033 {
3034 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.POS for type" << eomn_servicetype2string(mc_service.type);
3035 itisoksofar = false;
3036 }
3037
3038 if(false == has_PROPERTIES_JOINTMAPPING)
3039 {
3040 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING for type" << eomn_servicetype2string(mc_service.type);
3041 itisoksofar = false;
3042 }
3043
3044
3045 } break;
3046
3047 case eomn_serv_MC_advfoc:
3048 {
3049 // must have: ETHBOARD, CANBOARDS, JOINTMAPPING
3050
3051 itisoksofar = true;
3052
3053 if(false == has_PROPERTIES_ETHBOARD)
3054 {
3055 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD for type" << eomn_servicetype2string(mc_service.type);
3056 itisoksofar = false;
3057 }
3058
3059 if(false == has_PROPERTIES_CANBOARDS)
3060 {
3061 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS for type" << eomn_servicetype2string(mc_service.type);
3062 itisoksofar = false;
3063 }
3064
3065 if(false == has_PROPERTIES_JOINTMAPPING)
3066 {
3067 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING for type" << eomn_servicetype2string(mc_service.type);
3068 itisoksofar = false;
3069 }
3070
3071 } break;
3072
3073 default:
3074 {
3075 yError() << "ServiceParser::check_motion() has found an unknown type" << eomn_servicetype2string(mc_service.type);
3076 itisoksofar = false;
3077 } break;
3078 }
3079
3080 if(false == itisoksofar)
3081 {
3082 yError() << "ServiceParser::check_motion() detected missing groups in PROPERTIES";
3083 return false;
3084 }
3085
3086 // now i parse the groups
3087
3088 if(true == has_PROPERTIES_ETHBOARD)
3089 {
3090 // i get type
3091
3092 Bottle b_PROPERTIES_ETHBOARD_type = b_PROPERTIES_ETHBOARD.findGroup("type");
3093 if(b_PROPERTIES_ETHBOARD_type.isNull())
3094 {
3095 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.ETHBOARD.type";
3096 return false;
3097 }
3098
3099 // we must have only one board
3100 int numofethboards = b_PROPERTIES_ETHBOARD_type.size() - 1;
3101 if(1 != numofethboards)
3102 {
3103 yError() << "ServiceParser::check_motion() PROPERTIES.ETHBOARD.type must have one board only";
3104 return false;
3105 }
3106 if(false == convert(b_PROPERTIES_ETHBOARD_type.get(1).asString(), mc_service.properties.ethboardtype, formaterror))
3107 {
3108 yError() << "ServiceParser::check_motion() has found unknown SERVICE.PROPERTIES.ETHBOARD.type = " << b_PROPERTIES_ETHBOARD_type.get(1).asString();
3109 return false;
3110 }
3111
3112 } // has_PROPERTIES_ETHBOARD
3113
3114
3115 if(true == has_PROPERTIES_CANBOARDS)
3116 {
3117 // i get type, PROTOCOL.major/minor, FIRMWARE.major/minor/build and see their sizes. they must be all equal. i can have more than one board
3118
3119 Bottle b_PROPERTIES_CANBOARDS_type = b_PROPERTIES_CANBOARDS.findGroup("type");
3120 if(b_PROPERTIES_CANBOARDS_type.isNull())
3121 {
3122 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.type";
3123 return false;
3124 }
3125 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL = Bottle(b_PROPERTIES_CANBOARDS.findGroup("PROTOCOL"));
3126 if(b_PROPERTIES_CANBOARDS_PROTOCOL.isNull())
3127 {
3128 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.PROTOCOL";
3129 return false;
3130 }
3131 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL_major = Bottle(b_PROPERTIES_CANBOARDS_PROTOCOL.findGroup("major"));
3132 if(b_PROPERTIES_CANBOARDS_PROTOCOL_major.isNull())
3133 {
3134 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.PROTOCOL.major";
3135 return false;
3136 }
3137 Bottle b_PROPERTIES_CANBOARDS_PROTOCOL_minor = Bottle(b_PROPERTIES_CANBOARDS_PROTOCOL.findGroup("minor"));
3138 if(b_PROPERTIES_CANBOARDS_PROTOCOL_minor.isNull())
3139 {
3140 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.PROTOCOL.minor";
3141 return false;
3142 }
3143 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE = Bottle(b_PROPERTIES_CANBOARDS.findGroup("FIRMWARE"));
3144 if(b_PROPERTIES_CANBOARDS_FIRMWARE.isNull())
3145 {
3146 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.FIRMWARE";
3147 return false;
3148 }
3149 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_major = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("major"));
3150 if(b_PROPERTIES_CANBOARDS_FIRMWARE_major.isNull())
3151 {
3152 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.FIRMWARE.major";
3153 return false;
3154 }
3155 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_minor = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("minor"));
3156 if(b_PROPERTIES_CANBOARDS_FIRMWARE_minor.isNull())
3157 {
3158 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.FIRMWARE.minor";
3159 return false;
3160 }
3161 Bottle b_PROPERTIES_CANBOARDS_FIRMWARE_build = Bottle(b_PROPERTIES_CANBOARDS_FIRMWARE.findGroup("build"));
3162 if(b_PROPERTIES_CANBOARDS_FIRMWARE_build.isNull())
3163 {
3164 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.CANBOARDS.FIRMWARE.build";
3165 return false;
3166 }
3167
3168 size_t tmp = b_PROPERTIES_CANBOARDS_type.size();
3169 size_t numboards = (0 == tmp) ? 0 : (tmp - 1); // first position of bottle contains the tag "type"
3170
3171 // check if all other fields have the same size.
3172 if( (tmp != b_PROPERTIES_CANBOARDS_PROTOCOL_major.size()) ||
3173 (tmp != b_PROPERTIES_CANBOARDS_PROTOCOL_minor.size()) ||
3174 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_major.size()) ||
3175 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_minor.size()) ||
3176 (tmp != b_PROPERTIES_CANBOARDS_FIRMWARE_build.size())
3177 )
3178 {
3179 yError() << "ServiceParser::check_motion() in PROPERTIES.CANBOARDS some params have inconsistent lengths";
3180 return false;
3181 }
3182
3183
3185
3186 formaterror = false;
3187 for(size_t i=0; i<numboards; i++)
3188 {
3189 servCanBoard_t item;
3190
3191 convert(b_PROPERTIES_CANBOARDS_type.get(i+1).asString(), item.type, formaterror);
3192 convert(b_PROPERTIES_CANBOARDS_PROTOCOL_major.get(i+1).asInt32(), item.protocol.major, formaterror);
3193 convert(b_PROPERTIES_CANBOARDS_PROTOCOL_minor.get(i+1).asInt32(), item.protocol.minor, formaterror);
3194
3195 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_major.get(i+1).asInt32(), item.firmware.major, formaterror);
3196 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_minor.get(i+1).asInt32(), item.firmware.minor, formaterror);
3197 convert(b_PROPERTIES_CANBOARDS_FIRMWARE_build.get(i+1).asInt32(), item.firmware.build, formaterror);
3198
3199 mc_service.properties.canboards.push_back(item);
3200 }
3201
3202 // in here we could decide to return false if any previous conversion function has returned error
3203 // bool fromStringToBoolean(string str, bool &anyerror); // inside: if error then .... be sure to set error = true. dont set it to false.
3204
3205 if(true == formaterror)
3206 {
3207 yError() << "ServiceParser::check_motion() has detected an illegal format for some of the params of PROPERTIES.CANBOARDS some param has inconsistent length";
3208 return false;
3209 }
3210
3211 } // has_PROPERTIES_CANBOARDS
3212
3213
3214 if(true == has_PROPERTIES_MAIS)
3215 {
3216 // i get .location and nothing else
3217
3218 Bottle b_PROPERTIES_MAIS_location = b_PROPERTIES_MAIS.findGroup("location");
3219 if(b_PROPERTIES_MAIS_location.isNull())
3220 {
3221 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MAIS.location";
3222 return false;
3223 }
3224
3225 int tmp = b_PROPERTIES_MAIS_location.size();
3226 int numboards = tmp - 1; // first position of bottle contains the tag "location"
3227
3228 // check if numboards is 1.
3229 if(1 != numboards)
3230 {
3231 yError() << "ServiceParser::check_motion() in PROPERTIES.MAIS.location must contain one item only and it has:" << numboards;
3232 return false;
3233 }
3234
3235 formaterror = false;
3236 eObrd_location_t loc;
3237 if(false == convert(b_PROPERTIES_MAIS_location.get(1).asString(), loc, formaterror))
3238 {
3239 yError() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.MAIS.location";
3240 return false;
3241 }
3242
3243 if(eobrd_place_can == loc.any.place)
3244 {
3245 mc_service.properties.maislocation.port = loc.can.port;
3246 mc_service.properties.maislocation.addr = loc.can.addr;
3247 mc_service.properties.maislocation.insideindex = eobrd_caninsideindex_none;
3248 }
3249 else if(eobrd_place_extcan == loc.any.place)
3250 {
3251 mc_service.properties.maislocation.port = loc.extcan.port;
3252 mc_service.properties.maislocation.addr = loc.extcan.addr;
3253 mc_service.properties.maislocation.insideindex = eobrd_caninsideindex_none;
3254 }
3255 else
3256 {
3257 yError() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.MAIS.location. it must be either can or extcan";
3258 return false;
3259 }
3260
3261 } // has_PROPERTIES_MAIS
3262
3263
3264 if(true == has_PROPERTIES_MC4)
3265 {
3266 // i get:
3267 // SHIFTS.velocity/estimJointVelocity/estimJointAcceleration/estimMotorVelocity/estimMotorAcceleration,
3268 // BROADCASTPOLICY, JOINT2BOARD)
3269
3270 Bottle b_PROPERTIES_MC4_SHIFTS = Bottle(b_PROPERTIES_MC4.findGroup("SHIFTS"));
3271 if(b_PROPERTIES_MC4_SHIFTS.isNull())
3272 {
3273 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.SHIFTS";
3274 return false;
3275 }
3276
3277 Bottle b_PROPERTIES_MC4_SHIFTS_velocity = Bottle(b_PROPERTIES_MC4_SHIFTS.findGroup("velocity"));
3278 if(b_PROPERTIES_MC4_SHIFTS_velocity.isNull())
3279 {
3280 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.SHIFTS.velocity";
3281 return false;
3282 }
3283 Bottle b_PROPERTIES_MC4_SHIFTS_estimJointVelocity = Bottle(b_PROPERTIES_MC4_SHIFTS.findGroup("estimJointVelocity"));
3284 if(b_PROPERTIES_MC4_SHIFTS_estimJointVelocity.isNull())
3285 {
3286 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.SHIFTS.estimJointVelocity";
3287 return false;
3288 }
3289 Bottle b_PROPERTIES_MC4_SHIFTS_estimJointAcceleration = Bottle(b_PROPERTIES_MC4_SHIFTS.findGroup("estimJointAcceleration"));
3290 if(b_PROPERTIES_MC4_SHIFTS_estimJointAcceleration.isNull())
3291 {
3292 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.SHIFTS.estimJointAcceleration";
3293 return false;
3294 }
3295 Bottle b_PROPERTIES_MC4_SHIFTS_estimMotorVelocity = Bottle(b_PROPERTIES_MC4_SHIFTS.findGroup("estimMotorVelocity"));
3296 if(b_PROPERTIES_MC4_SHIFTS_estimMotorVelocity.isNull())
3297 {
3298 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.SHIFTS.estimMotorVelocity";
3299 return false;
3300 }
3301 Bottle b_PROPERTIES_MC4_SHIFTS_estimMotorAcceleration = Bottle(b_PROPERTIES_MC4_SHIFTS.findGroup("estimMotorAcceleration"));
3302 if(b_PROPERTIES_MC4_SHIFTS_estimMotorAcceleration.isNull())
3303 {
3304 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.SHIFTS.estimMotorAcceleration";
3305 return false;
3306 }
3307
3308 Bottle b_PROPERTIES_MC4_BROADCASTPOLICY = Bottle(b_PROPERTIES_MC4.findGroup("BROADCASTPOLICY"));
3309 if(b_PROPERTIES_MC4_BROADCASTPOLICY.isNull())
3310 {
3311 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.BROADCASTPOLICY";
3312 return false;
3313 }
3314
3315 Bottle b_PROPERTIES_MC4_BROADCASTPOLICY_enable = Bottle(b_PROPERTIES_MC4_BROADCASTPOLICY.findGroup("enable"));
3316 if(b_PROPERTIES_MC4_BROADCASTPOLICY_enable.isNull())
3317 {
3318 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.BROADCASTPOLICY.enable";
3319 return false;
3320 }
3321
3322/* Bottle b_PROPERTIES_MC4_JOINT2BOARD = Bottle(b_PROPERTIES_MC4.findGroup("JOINT2BOARD"));
3323 if(b_PROPERTIES_MC4_JOINT2BOARD.isNull())
3324 {
3325 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.JOINT2BOARD";
3326 return false;
3327 }
3328
3329 Bottle b_PROPERTIES_MC4_JOINT2BOARD_location = Bottle(b_PROPERTIES_MC4_JOINT2BOARD.findGroup("location"));
3330 if(b_PROPERTIES_MC4_JOINT2BOARD_location.isNull())
3331 {
3332 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.MC4.JOINT2BOARD.location";
3333 return false;
3334 }
3335*/
3336 // 1. get values for SHIFTS
3337
3338 uint8_t value = 0;
3339 if(true == convert(b_PROPERTIES_MC4_SHIFTS_velocity.get(1).asInt32(), value, formaterror))
3340 {
3341 mc_service.properties.mc4shifts.velocity = value;
3342 }
3343 if(true == convert(b_PROPERTIES_MC4_SHIFTS_estimJointVelocity.get(1).asInt32(), value, formaterror))
3344 {
3345 if(value > 15)
3346 {
3347 yError() << "ServiceParser::check_motion() manages values of PROPERTIES.MC4.SHIFTS.estim* only in range [0, 15]. read value =" << value;
3348 return false;
3349 }
3350 mc_service.properties.mc4shifts.estimJointVelocity = value;
3351 }
3352 if(true == convert(b_PROPERTIES_MC4_SHIFTS_estimJointAcceleration.get(1).asInt32(), value, formaterror))
3353 {
3354 if(value > 15)
3355 {
3356 yError() << "ServiceParser::check_motion() manages values of PROPERTIES.MC4.SHIFTS.estim* only in range [0, 15]. read value =" << value;
3357 return false;
3358 }
3359 mc_service.properties.mc4shifts.estimJointAcceleration = value;
3360 }
3361 if(true == convert(b_PROPERTIES_MC4_SHIFTS_estimMotorVelocity.get(1).asInt32(), value, formaterror))
3362 {
3363 if(value > 15)
3364 {
3365 yError() << "ServiceParser::check_motion() manages values of PROPERTIES.MC4.SHIFTS.estim* only in range [0, 15]. read value =" << value;
3366 return false;
3367 }
3368 mc_service.properties.mc4shifts.estimMotorVelocity = value;
3369 }
3370 if(true == convert(b_PROPERTIES_MC4_SHIFTS_estimMotorAcceleration.get(1).asInt32(), value, formaterror))
3371 {
3372 if(value > 15)
3373 {
3374 yError() << "ServiceParser::check_motion() manages values of PROPERTIES.MC4.SHIFTS.estim* only in range [0, 15]. read value =" << value;
3375 return false;
3376 }
3377 mc_service.properties.mc4shifts.estimMotorAcceleration = value;
3378 }
3379
3380 // 2. i get the values for b_PROPERTIES_MC4_BROADCASTPOLICY_enable
3381
3382 int tmp = b_PROPERTIES_MC4_BROADCASTPOLICY_enable.size();
3383 int numofenables = tmp - 1; // first position of bottle contains the tag "enable"
3384
3386 for(int i=0; i<numofenables; i++)
3387 {
3388 // transform the string into a value.
3389 eOmc_mc4broadcast_t item = eomc_mc4broadcast_unknown;
3390 const char *str = b_PROPERTIES_MC4_BROADCASTPOLICY_enable.get(i+1).asString().c_str();
3391
3392 // check compact and then non-compact form
3393 if(eomc_mc4broadcast_unknown == (item = eomc_string2mc4broadcast(str, eobool_true)))
3394 {
3395 item = eomc_string2mc4broadcast(str, eobool_false);
3396 }
3397
3398 if((eomc_mc4broadcast_unknown != item) && (eomc_mc4broadcast_none != item))
3399 { // if meaningful ...
3400 mc_service.properties.mc4broadcasts.push_back(item);
3401 }
3402 }
3403
3404
3405
3406 // 3. i get the values for b_PROPERTIES_MC4_JOINT2BOARD_location.... there must be 12 values
3407
3408/* int tmp1 = b_PROPERTIES_MC4_JOINT2BOARD_location.size();
3409 int numoflocations = tmp1 - 1; // first position of bottle contains the tag "location"
3410
3411 if(12 != numoflocations)
3412 {
3413 yError() << "ServiceParser::check_motion() detects that PROPERTIES.MC4.JOINT2BOARD.location has not 12 items but" << numoflocations;
3414 return false;
3415 }
3416
3417 mc_service.properties.mc4joints.resize(0);
3418 for(int i=0; i<numoflocations; i++)
3419 {
3420 // transform the string into a location
3421
3422 formaterror = false;
3423 eObrd_location_t loc;
3424 if(false == convert(b_PROPERTIES_MC4_JOINT2BOARD_location.get(i+1).asString(), loc, formaterror))
3425 {
3426 yError() << "ServiceParser::check_motion() has detected an illegal format for PROPERTIES.MC4.JOINT2BOARD.location";
3427 return false;
3428 }
3429
3430 eObrd_canlocation_t item;
3431 if(eobrd_place_extcan == loc.any.place)
3432 {
3433 item.port = loc.extcan.port;
3434 item.addr = loc.extcan.addr;
3435 item.insideindex = loc.extcan.index;
3436 }
3437 else
3438 {
3439 yError() << "ServiceParser::check_motion() has detected an illegal format for PROPERTIES.MC4.JOINT2BOARD.location. it must be extcan";
3440 return false;
3441 }
3442
3443 mc_service.properties.mc4joints.push_back(item);
3444 }
3445*/
3446
3447 } // has_PROPERTIES_MC4
3448
3449 if(true == has_PROPERTIES_PSC)
3450 {
3451 // i get .location and nothing else
3452
3453 Bottle b_PROPERTIES_PSC_location = b_PROPERTIES_PSC.findGroup("location");
3454 if(b_PROPERTIES_PSC_location.isNull())
3455 {
3456 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.PSC.location";
3457 return false;
3458 }
3459
3460 int tmp = b_PROPERTIES_PSC_location.size();
3461 int numboards = tmp - 1; // first position of bottle contains the tag "location"
3462
3463 // check if numboards is 3.
3464 if(eOas_psc_boards_maxnumber != numboards)
3465 {
3466 yError() << "ServiceParser::check_motion() in PROPERTIES.PSC.location must contain three items and it has:" << numboards;
3467 return false;
3468 }
3469
3471 for(int i=0; i<3; i++)
3472 {
3473 eObrd_location_t loc;
3474 formaterror = false;
3475 if(false == convert(b_PROPERTIES_PSC_location.get(1+i).asString(), loc, formaterror))
3476 {
3477 yError() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.PSC.location";
3478 return false;
3479 }
3480
3481 if(eobrd_place_can == loc.any.place)
3482 {
3483 mc_service.properties.psclocations[i].port = loc.can.port;
3484 mc_service.properties.psclocations[i].addr = loc.can.addr;
3485 mc_service.properties.psclocations[i].insideindex = eobrd_caninsideindex_none;
3486
3487 }
3488 else if(eobrd_place_extcan == loc.any.place)
3489 {
3490 mc_service.properties.psclocations[i].port = loc.extcan.port;
3491 mc_service.properties.psclocations[i].addr = loc.extcan.addr;
3492 mc_service.properties.psclocations[i].insideindex = eobrd_caninsideindex_none;
3493 }
3494 else
3495 {
3496 yError() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.PSC.location. it must be either can or extcan";
3497 return false;
3498 }
3499 }
3500
3501 } // has_PROPERTIES_PSC
3502
3503
3504 if(true == has_PROPERTIES_POS)
3505 {
3506 // i get .location and nothing else
3507
3508 Bottle b_PROPERTIES_POS_location = b_PROPERTIES_POS.findGroup("location");
3509 if(b_PROPERTIES_POS_location.isNull())
3510 {
3511 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.POS.location";
3512 return false;
3513 }
3514
3515 int tmp = b_PROPERTIES_POS_location.size();
3516 int numboards = tmp - 1; // first position of bottle contains the tag "location"
3517
3518 // check if numboards is 1.
3519 constexpr uint8_t wantedboards = 1;
3520 if(wantedboards != numboards)
3521 {
3522 yError() << "ServiceParser::check_motion() in PROPERTIES.POS.location must contain " << wantedboards << " items and it has:" << numboards;
3523 return false;
3524 }
3525
3526 mc_service.properties.poslocations.resize(wantedboards);
3527 for(int i=0; i<wantedboards; i++)
3528 {
3529 eObrd_location_t loc;
3530 formaterror = false;
3531 if(false == convert(b_PROPERTIES_POS_location.get(1+i).asString(), loc, formaterror))
3532 {
3533 yError() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.POS.location";
3534 return false;
3535 }
3536
3537 if(eobrd_place_can == loc.any.place)
3538 {
3539 mc_service.properties.poslocations[i].port = loc.can.port;
3540 mc_service.properties.poslocations[i].addr = loc.can.addr;
3541 mc_service.properties.poslocations[i].insideindex = eobrd_caninsideindex_none;
3542
3543 }
3544 else if(eobrd_place_extcan == loc.any.place)
3545 { // for pos service we should not have such a format
3546 yError() << "ServiceParser::check_motion() has detected an incorrect format for SERVICE.PROPERTIES.POS.location. it must be either can, not extcan";
3547 mc_service.properties.poslocations[i].port = loc.extcan.port;
3548 mc_service.properties.poslocations[i].addr = loc.extcan.addr;
3549 mc_service.properties.poslocations[i].insideindex = eobrd_caninsideindex_none;
3550 }
3551 else
3552 {
3553 yError() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.POS.location. it must be can";
3554 return false;
3555 }
3556 }
3557
3558 } // has_PROPERTIES_POS
3559
3560 if(true == has_PROPERTIES_JOINTMAPPING)
3561 {
3562
3563 // actuator, encoder1, encoder2 must all be present. the params contained inside must be all of equal length and equal to numberofjoints
3564
3565 Bottle b_PROPERTIES_JOINTMAPPING_ACTUATOR = Bottle(b_PROPERTIES_JOINTMAPPING.findGroup("ACTUATOR"));
3566 if(b_PROPERTIES_JOINTMAPPING_ACTUATOR.isNull())
3567 {
3568 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ACTUATOR";
3569 return false;
3570 }
3571
3572 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER1 = Bottle(b_PROPERTIES_JOINTMAPPING.findGroup("ENCODER1"));
3573 if(b_PROPERTIES_JOINTMAPPING_ENCODER1.isNull())
3574 {
3575 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER1";
3576 return false;
3577 }
3578
3579 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER2 = Bottle(b_PROPERTIES_JOINTMAPPING.findGroup("ENCODER2"));
3580 if(b_PROPERTIES_JOINTMAPPING_ENCODER2.isNull())
3581 {
3582 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER2";
3583 return false;
3584 }
3585
3586 // now the vectors the above three contain ...
3587
3588 Bottle b_PROPERTIES_JOINTMAPPING_ACTUATOR_type = Bottle(b_PROPERTIES_JOINTMAPPING_ACTUATOR.findGroup("type"));
3589 if(b_PROPERTIES_JOINTMAPPING_ACTUATOR_type.isNull())
3590 {
3591 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ACTUATOR.type";
3592 return false;
3593 }
3594
3595 Bottle b_PROPERTIES_JOINTMAPPING_ACTUATOR_onboard = Bottle(b_PROPERTIES_JOINTMAPPING_ACTUATOR.findGroup("onboard"));
3596 // mandatory only for advfoc
3597
3598 Bottle b_PROPERTIES_JOINTMAPPING_ACTUATOR_port = Bottle(b_PROPERTIES_JOINTMAPPING_ACTUATOR.findGroup("port"));
3599 if(b_PROPERTIES_JOINTMAPPING_ACTUATOR_port.isNull())
3600 {
3601 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ACTUATOR.port";
3602 return false;
3603 }
3604
3605 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER1_type = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER1.findGroup("type"));
3606 if(b_PROPERTIES_JOINTMAPPING_ENCODER1_type.isNull())
3607 {
3608 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER1.type";
3609 return false;
3610 }
3611 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER1_port = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER1.findGroup("port"));
3612 if(b_PROPERTIES_JOINTMAPPING_ENCODER1_port.isNull())
3613 {
3614 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER1.port";
3615 return false;
3616 }
3617 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER1_position = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER1.findGroup("position"));
3618 if(b_PROPERTIES_JOINTMAPPING_ENCODER1_position.isNull())
3619 {
3620 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER1.position";
3621 return false;
3622 }
3623 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER1_resolution = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER1.findGroup("resolution"));
3624 if(b_PROPERTIES_JOINTMAPPING_ENCODER1_resolution.isNull())
3625 {
3626 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER1.resolution";
3627 return false;
3628 }
3629 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER1_tolerance = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER1.findGroup("tolerance"));
3630 if(b_PROPERTIES_JOINTMAPPING_ENCODER1_tolerance.isNull())
3631 {
3632 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER1.tolerance";
3633 return false;
3634 }
3635
3636
3637
3638 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER2_type = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER2.findGroup("type"));
3639 if(b_PROPERTIES_JOINTMAPPING_ENCODER2_type.isNull())
3640 {
3641 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER2.type";
3642 return false;
3643 }
3644 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER2_port = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER2.findGroup("port"));
3645 if(b_PROPERTIES_JOINTMAPPING_ENCODER2_port.isNull())
3646 {
3647 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER2.port";
3648 return false;
3649 }
3650 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER2_position = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER2.findGroup("position"));
3651 if(b_PROPERTIES_JOINTMAPPING_ENCODER2_position.isNull())
3652 {
3653 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER2.position";
3654 return false;
3655 }
3656 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER2_resolution = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER2.findGroup("resolution"));
3657 if(b_PROPERTIES_JOINTMAPPING_ENCODER2_resolution.isNull())
3658 {
3659 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER2.resolution";
3660 return false;
3661 }
3662 Bottle b_PROPERTIES_JOINTMAPPING_ENCODER2_tolerance = Bottle(b_PROPERTIES_JOINTMAPPING_ENCODER2.findGroup("tolerance"));
3663 if(b_PROPERTIES_JOINTMAPPING_ENCODER2_tolerance.isNull())
3664 {
3665 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ENCODER2.tolerance";
3666 return false;
3667 }
3668 // now the size of the vectors must all be equal
3669
3670 size_t tmp = b_PROPERTIES_JOINTMAPPING_ACTUATOR_type.size();
3671 if( (tmp != b_PROPERTIES_JOINTMAPPING_ACTUATOR_port.size()) ||
3672 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER1_type.size()) ||
3673 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER1_port.size()) ||
3674 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER1_position.size()) ||
3675 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER1_resolution.size())||
3676 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER1_tolerance.size()) ||
3677 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER2_type.size()) ||
3678 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER2_port.size()) ||
3679 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER2_position.size()) ||
3680 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER2_resolution.size()) ||
3681 (tmp != b_PROPERTIES_JOINTMAPPING_ENCODER2_tolerance.size())
3682 )
3683 {
3684 yError() << "ServiceParser::check_motion() detected wrong number of columns somewhere inside PROPERTIES.JOINTMAPPING";
3685 return false;
3686 }
3687
3688 // ok, we have the number of joints .........
3689 mc_service.properties.numofjoints = (0 == tmp ) ? (0) : (tmp-1);
3690
3691 // i attempt to parse the vectors inside actuators (type, port), encoder1 (type, port, position) and encoder2 (type, port, position).
3692
3696
3697 if(eomn_serv_MC_mc4 == mc_service.type)
3698 {
3700 }
3701
3702
3703 for(int i=0; i<mc_service.properties.numofjoints; i++)
3704 {
3706 servMC_encoder_t enc1;
3707 servMC_encoder_t enc2;
3708 bool formaterror = false;
3709
3710 eOmc_encoder_t enctype = eomc_enc_unknown;
3711 uint8_t encport = eobrd_port_unknown;
3712 eOmc_position_t encposition = eomc_pos_unknown;
3713
3714 // actuators ..
3715 act.type = eomc_act_unknown;
3716 act.desc.pwm.port = eobrd_port_unknown;
3717
3718 if(false == convert(b_PROPERTIES_JOINTMAPPING_ACTUATOR_type.get(i+1).asString(), act.type, formaterror))
3719 {
3720 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.actuator.type not valid for item" << i;
3721 return false;
3722 }
3723
3724 if((eomn_serv_MC_mc4 == mc_service.type) && (eomc_act_mc4 != act.type))
3725 {
3726 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.actuator.type should be mc4 with mc service of type eomn_serv_MC_mc4. Error in item" << i;
3727 return false;
3728 }
3729
3730 if(false == parse_actuator_port(b_PROPERTIES_JOINTMAPPING_ACTUATOR_port.get(i+1).asString(), mc_service.properties.ethboardtype, act.type, act.desc, formaterror))
3731 {
3732 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.actuator.port not valid for item" << i;
3733 return false;
3734 }
3735
3736 if(eomn_serv_MC_mc4 == mc_service.type)
3737 {
3738 eObrd_canlocation_t item;
3739 item.port = act.desc.mc4.canloc.port;
3740 item.addr = act.desc.mc4.canloc.addr;
3741 item.insideindex = act.desc.mc4.canloc.insideindex;
3742
3743 mc_service.properties.mc4joints.push_back(item);
3744 }
3745
3746 if(eomn_serv_MC_advfoc == mc_service.type)
3747 {
3748 if(b_PROPERTIES_JOINTMAPPING_ACTUATOR_onboard.isNull())
3749 {
3750 yError() << "ServiceParser::check_motion() cannot find PROPERTIES.JOINTMAPPING.ACTUATOR.onboard for eomn_serv_MC_advfoc";
3751 return false;
3752 }
3753
3754 if(act.type != eomc_act_advfoc)
3755 {
3756 yError() << "ServiceParser::check_motion() detectde that PROPERTIES.JOINTMAPPING.ACTUATOR.type for eomn_serv_MC_advfoc id not advfoc";
3757 return false;
3758 }
3759
3760 act.advdescr.type = eomc_act_advfoc;
3761 act.advdescr.location = act.desc.gen.location;
3762 eObrd_cantype_t bb {};
3763 convert(b_PROPERTIES_JOINTMAPPING_ACTUATOR_onboard.get(i+1).asString(), bb, formaterror);
3764 act.advdescr.board.type = bb;
3765 }
3766
3767
3768 // encoder1s ...
3769
3770 enc1.desc.type = eomc_enc_unknown;
3771 enc1.desc.port = eobrd_port_unknown;
3772 enc1.desc.pos = eomc_pos_unknown;
3773
3774 enctype = eomc_enc_unknown;
3775 if(false == convert(b_PROPERTIES_JOINTMAPPING_ENCODER1_type.get(i+1).asString(), enctype, formaterror))
3776 {
3777 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.encoder1.type not valid for item" << i;
3778 return false;
3779 }
3780 enc1.desc.type = enctype;
3781
3782 // depending on type, we ....
3783
3784
3785
3786 // dobbiamo fare un parser che riconosca CONN:P6 se aea, qenc etc, oppure MAIS:thumbproximal se mais
3787
3788 encport = eobrd_port_unknown;
3789 if(false == parse_encoder_port(b_PROPERTIES_JOINTMAPPING_ENCODER1_port.get(i+1).asString(), mc_service.properties.ethboardtype, enctype, encport, formaterror))
3790 {
3791 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.encoder1.port not valid for item" << i;
3792 return false;
3793 }
3794 enc1.desc.port = encport;
3795
3796 encposition = eomc_pos_unknown;
3797 if(false == convert(b_PROPERTIES_JOINTMAPPING_ENCODER1_position.get(i+1).asString(), encposition, formaterror))
3798 {
3799 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.encoder1.position not valid for item" << i;
3800 return false;
3801 }
3802 enc1.desc.pos = encposition;
3803
3804 enc1.resolution = b_PROPERTIES_JOINTMAPPING_ENCODER1_resolution.get(i+1).asInt32();
3805
3806 enc1.tolerance = b_PROPERTIES_JOINTMAPPING_ENCODER1_tolerance.get(i+1).asFloat64();
3807
3808
3809
3810 // encoder2s ...
3811
3812 enc2.desc.type = eomc_enc_unknown;
3813 enc2.desc.port = eobrd_port_unknown;
3814 enc2.desc.pos = eomc_pos_unknown;
3815
3816 enctype = eomc_enc_unknown;
3817 if(false == convert(b_PROPERTIES_JOINTMAPPING_ENCODER2_type.get(i+1).asString(), enctype, formaterror))
3818 {
3819 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.encoder2.type not valid for item" << i;
3820 return false;
3821 }
3822
3823 enc2.desc.type = enctype;
3824
3825
3826 encport = eobrd_port_unknown;
3827 if(false == parse_encoder_port(b_PROPERTIES_JOINTMAPPING_ENCODER2_port.get(i+1).asString(), mc_service.properties.ethboardtype, enctype, encport, formaterror))
3828 {
3829 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.encoder2.port not valid for item" << i;
3830 return false;
3831 }
3832 enc2.desc.port = encport;
3833
3834 encposition = eomc_pos_unknown;
3835 if(false == convert(b_PROPERTIES_JOINTMAPPING_ENCODER2_position.get(i+1).asString(), encposition, formaterror))
3836 {
3837 yError() << "ServiceParser::check_motion() PROPERTIES.JOINTMAPPING.encoder2.position not valid for item" << i;
3838 return false;
3839 }
3840
3841 enc2.desc.pos = encposition;
3842
3843 enc2.resolution = b_PROPERTIES_JOINTMAPPING_ENCODER2_resolution.get(i+1).asInt32();
3844 enc2.tolerance = b_PROPERTIES_JOINTMAPPING_ENCODER2_tolerance.get(i+1).asFloat64();
3845
3846
3847 // ok, we push act, enc1, enc2
3848
3849 mc_service.properties.actuators.push_back(act);
3850 mc_service.properties.encoder1s.push_back(enc1);
3851 mc_service.properties.encoder2s.push_back(enc2);
3852
3853 }
3854
3855 } // has_PROPERTIES_JOINTMAPPING
3856
3857
3858 // add default values. then we may change tem
3859 mc_service.diagconfig.mode = eomn_serv_diagn_mode_NONE;
3860 mc_service.diagconfig.par16 = 0;
3861
3862 if(true == has_PROPERTIES_DIAGNOSTICS)
3863 {
3864 Bottle b_PROPERTIES_DIAGNOSTICS_mode = b_PROPERTIES_DIAGNOSTICS.findGroup("mode");
3865 Bottle b_PROPERTIES_DIAGNOSTICS_par16 = b_PROPERTIES_DIAGNOSTICS.findGroup("par16");
3866 if(!b_PROPERTIES_DIAGNOSTICS_mode.isNull() && !b_PROPERTIES_DIAGNOSTICS_par16.isNull())
3867 {
3868 // if we have both of them ... and they contain at least (only) one we get the values
3869 int n_type = b_PROPERTIES_DIAGNOSTICS_mode.size() - 1;
3870 int n_par16 = b_PROPERTIES_DIAGNOSTICS_par16.size() - 1;
3871 if((1 == n_type) && (1 == n_par16))
3872 {
3873 eOmn_serv_diagn_mode_t dm = eomn_serv_diagn_mode_NONE;
3874 int par16 = 0;
3875 if(false == convert(b_PROPERTIES_DIAGNOSTICS_mode.get(1).asString(), dm, formaterror))
3876 {
3877 yWarning() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.DIAGNOSTICS.mode. Using {eOmn_serv_diagn_mode_NONE, 0}";
3878 }
3879 else if(!b_PROPERTIES_DIAGNOSTICS_par16.get(1).isInt32())
3880 {
3881 yWarning() << "ServiceParser::check_motion() has detected an illegal format for SERVICE.PROPERTIES.DIAGNOSTICS.par16. Using {eOmn_serv_diagn_mode_NONE, 0}";
3882 }
3883 else
3884 {
3885 par16 = b_PROPERTIES_DIAGNOSTICS_par16.get(1).asInt32();
3886 }
3887
3888 mc_service.diagconfig.mode = dm;
3889 mc_service.diagconfig.par16 = static_cast<uint16_t>(par16);
3890
3891 yWarning() << "ServiceParser::check_motion() has detected some DIAGNOSTICS config for this MC service: mode = " << eomn_servicediagnmode2string(dm) << ", par16 = " << mc_service.diagconfig.par16;
3892
3893 }
3894
3895 }
3896
3897 } // has_PROPERTIES_DIAGNOSTICS
3898
3899
3900 return true;
3901}
3902
3903// int ServiceParser::getnumofjointsets(void)
3904// {
3905//
3906// int n=0;
3907// int njointsinset[mc_service.properties.numofjoints]; //the max number of sets is equal to max number of joints.
3908// for(int i=0; i<mc_service.properties.numofjoints;i++)
3909// {
3910// njointsinset[i] = 0;
3911// }
3912//
3913// for(int i=0; i<mc_service.properties.numofjoints;i++)
3914// {
3915// int set = mc_service.properties.joint2set[i];
3916//
3917// if(set > mc_service.properties.numofjoints)
3918// {
3919// yError() << "ServiceParser::getnumofjointsets: error in joint2set param. The set number is too big. Remember: max number of set is equal to max num of joint.";
3920// return false;
3921// }
3922//
3923// njointsinset[set]++;
3924// }
3925// int count =0;
3926// for(int i=0; i<mc_service.properties.numofjoints;i++)
3927// {
3928// if(njointsinset[i] != 0)
3929// count++;
3930// }
3931//
3932// return count;
3933// }
3934
3935
3936//bool ServiceParser::parseMCEncoderItem(Bottle &b_ENCODER, vector<servMC_encoder_t> &encoders, char *encString)
3937//{
3938//#warning -> correct warnings on
3939//
3940// Bottle b_ENCODER_TYPE(b_ENCODER.find("type").asString());
3941// if(b_ENCODER_TYPE.isNull())
3942// {
3943// yError() << "ServiceParser::parseMCEncoderItem() cannot find JOINTMAPPING."<< encString<< ".type";
3944// return false;
3945// }
3946//
3947// Bottle b_ENCODER_PORT(b_ENCODER.find("port").asString());
3948// if(b_ENCODER_PORT.isNull())
3949// {
3950// yError() << "ServiceParser::parseMCEncoderItem() cannot find JOINTMAPPING"<< encString<< ".type";
3951// return false;
3952// }
3953//
3954// encoders.resize(0);
3955// int numofenc = b_ENCODER_TYPE.size() -1;
3956//
3957// //VALE: controlla che il numero di act sia uguale a quello di joint per embobjmotion control obj!!!
3958// for(int i = 0; i< numofenc; i++)
3959// {
3960// servMC_encoder_t item;
3961// bool formaterror = false;
3962// if(false == convert(b_ENCODER_TYPE.get(i+1).asString(), item.type, formaterror))
3963// {
3964// yError() << "ServiceParser::parseMCEncoderItem() encoder type not valid in " << encString;
3965// return false;
3966// }
3967// //VALE: commented in ordet to compile I have not enouth time to implement this function
3973//
3974// if(false == convert(b_ENCODER_TYPE.get(i+1).asString(), item.position, formaterror))
3975// {
3976// yError() << "ServiceParser::parseMCEncoderItem() encoder location not valid in " << encString;
3977// return false;
3978// }
3979// encoders.push_back(item);
3980//
3981// }
3982// return true;
3983//}
3984
3985
3986// bool ServiceParser::copyjomocouplingInfo( eOmc_4jomo_coupling_t *jc_dest)
3987// {
3988//
3989// memset(jc_dest, 0, sizeof(eOmc_4jomo_coupling_t));
3990//
3991// // very important: so far, the fw in Controller.c must find eomc_jointSetNum_none in un-used entries, even if we have less than 4 joints.
3992// memset(jc_dest->joint2set, eomc_jointSetNum_none, sizeof(jc_dest->joint2set));
3993//
3994// for(int i=0; i<mc_service.properties.numofjoints; i++)
3995// {
3996// jc_dest->joint2set[i] = mc_service.properties.joint2set[i];
3997// }
3998//
3999// for(int i=0; i<4; i++)
4000// {
4001// for(int j=0; j<4; j++)
4002// {
4003// jc_dest->joint2motor[i][j] = eo_common_float_to_Q17_14(mc_service.properties.controller.matrixJ2M[4*i+j]);
4004// jc_dest->motor2joint[i][j] = eo_common_float_to_Q17_14(mc_service.properties.controller.matrixM2J[4*i+j]);
4005// }
4006// }
4007//
4008//
4009// for(int r=0; r<4; r++)
4010// {
4011// for(int c=0; c<6; c++)
4012// {
4013// jc_dest->encoder2joint[r][c] = eo_common_float_to_Q17_14(mc_service.properties.controller.matrixE2J[6*r+c]);
4014// }
4015// }
4016//
4017// for(int s=0; s< mc_service.properties.numofjointsets; s++)
4018// {
4019// memcpy(&jc_dest->jsetcfg[s] , &mc_service.properties.jointset_cfgs[s], sizeof(eOmc_jointset_configuration_t));
4020// }
4021//
4022// return true;
4023// }
4024
4025
4026
4027bool ServiceParser::parseService(Searchable &config, servConfigMC_t &mcconfig)
4028{
4029 bool ret = false;
4030
4031 if(false == check_motion(config))
4032 {
4033 yError() << "ServiceParser::parseService() gets same errors parsing SERVICE MC group";
4034 return ret;
4035 }
4036
4037 // if we dont find the xml file ... we just return true but mc_service.type is eomn_serv_MC_generic.
4038 // in such a case we dont transmit the config and ask the eth board to config itself accoring to its ip address.
4039 // ...
4040
4041 mcconfig.ethservice.configuration.type = mc_service.type;
4042 mcconfig.ethservice.configuration.diagnosticsmode = mc_service.diagconfig.mode;
4043 mcconfig.ethservice.configuration.diagnosticsparam = mc_service.diagconfig.par16;
4044
4045 switch(mc_service.type)
4046 {
4047 case eomn_serv_MC_foc:
4048 {
4049 eOmn_serv_config_data_mc_foc_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.foc_based);
4050
4051 // 1. ->version (of foc board).
4052 data_mc->version.firmware.major = mc_service.properties.canboards.at(0).firmware.major;
4053 data_mc->version.firmware.minor = mc_service.properties.canboards.at(0).firmware.minor;
4054 data_mc->version.firmware.build = mc_service.properties.canboards.at(0).firmware.build;
4055 data_mc->version.protocol.major = mc_service.properties.canboards.at(0).protocol.major;
4056 data_mc->version.protocol.minor = mc_service.properties.canboards.at(0).protocol.minor;
4057
4058 // we assume that all can boards have the same type for each joint
4059 data_mc->type = mc_service.properties.canboards.at(0).type;
4060
4061 // 2. ->arrayofjomodescriptors
4062 EOarray *arrayofjomos = eo_array_New(4, sizeof(eOmc_jomo_descriptor_t), &data_mc->arrayofjomodescriptors);
4063 int numofjomos = mc_service.properties.numofjoints;
4064
4065 for(int i=0; i<numofjomos; i++)
4066 {
4067 eOmc_jomo_descriptor_t jomodes = {};
4068
4069 // 1. actuator is on foc: we need the address
4070 jomodes.actuator.foc.canloc.port = mc_service.properties.actuators[i].desc.foc.canloc.port;
4071 jomodes.actuator.foc.canloc.addr = mc_service.properties.actuators[i].desc.foc.canloc.addr;
4072 jomodes.actuator.foc.canloc.insideindex = eobrd_caninsideindex_first;
4073
4074 // 2. encoder1 is ...
4075 jomodes.encoder1.type = mc_service.properties.encoder1s[i].desc.type;
4076 jomodes.encoder1.port = mc_service.properties.encoder1s[i].desc.port;
4077 jomodes.encoder1.pos = mc_service.properties.encoder1s[i].desc.pos;
4078
4079 // 3. encoder2 is ...
4080 jomodes.encoder2.type = mc_service.properties.encoder2s[i].desc.type;
4081 jomodes.encoder2.port = mc_service.properties.encoder2s[i].desc.port;
4082 jomodes.encoder2.pos = mc_service.properties.encoder2s[i].desc.pos;
4083
4084 eo_array_PushBack(arrayofjomos, &jomodes);
4085
4086 }
4087
4088
4090 //eOmc_4jomo_coupling_t *jomocoupling = &data_mc->jomocoupling;
4091
4092 //ret = copyjomocouplingInfo(jomocoupling);
4093
4094 // ok, everything is done
4095 ret = true;
4096
4097 } break;
4098
4099 case eomn_serv_MC_mc4:
4100 {
4101 eOmn_serv_config_data_mc_mc4_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.mc4_based);
4102
4103 // 1. ->version (of mc4 board) + ->mais.version.
4104 bool mc4boardFound = false;
4105 bool maisboardFound = false;
4106 for(size_t i=0; i<mc_service.properties.canboards.size(); i++)
4107 {
4108 if(eobrd_cantype_mc4 == mc_service.properties.canboards[i].type)
4109 {
4110 data_mc->mc4version.protocol = mc_service.properties.canboards[i].protocol;
4111 data_mc->mc4version.firmware = mc_service.properties.canboards[i].firmware;
4112 mc4boardFound = true;
4113 }
4114 else if(eobrd_cantype_mais == mc_service.properties.canboards[i].type)
4115 {
4116 data_mc->mais.version.protocol = mc_service.properties.canboards[i].protocol;
4117 data_mc->mais.version.firmware = mc_service.properties.canboards[i].firmware;
4118 maisboardFound = true;
4119 }
4120 }
4121
4122 if((false == maisboardFound) || (false == mc4boardFound))
4123 {
4124 yError() << "ServiceParser::parseService() gets same errors parsing SERVICE MC group for mc4: cannot find description of mc4 or mais board";
4125 }
4126
4127// data_mc->mc4version.firmware.major = mc_service.properties.canboards.at(0).firmware.major;
4128// data_mc->mc4version.firmware.minor = mc_service.properties.canboards.at(0).firmware.minor;
4129// data_mc->mc4version.firmware.build = mc_service.properties.canboards.at(0).firmware.build;
4130// data_mc->mc4version.protocol.major = mc_service.properties.canboards.at(0).protocol.major;
4131// data_mc->mc4version.protocol.minor = mc_service.properties.canboards.at(0).protocol.minor;
4132
4133 // 2. ->mc4shifts
4134 data_mc->mc4shifts = mc_service.properties.mc4shifts;
4135
4136 // 3. ->mc4joints
4137 for(int i=0; i<12; i++)
4138 {
4139 data_mc->mc4joints[i] = mc_service.properties.mc4joints[i];
4140 }
4141
4142
4143 // 4. ->mais.canloc
4144 data_mc->mais.canloc = mc_service.properties.maislocation;
4145
4146 // 5. ->broadcastflags
4147 data_mc->broadcastflags = 0;
4148 for(size_t i=0; i<mc_service.properties.mc4broadcasts.size(); i++)
4149 {
4150 eOmc_mc4broadcast_t item = mc_service.properties.mc4broadcasts[i];
4151 if((eomc_mc4broadcast_none != item) && (eomc_mc4broadcast_unknown != item))
4152 {
4153 eo_common_hlfword_bitset(&data_mc->broadcastflags, item);
4154 }
4155 }
4156
4157 // ok, everything is done
4158 ret = true;
4159
4160 } break;
4161
4162 case eomn_serv_MC_mc4plus:
4163 {
4164 eOmn_serv_config_data_mc_mc4plus_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.mc4plus_based);
4165
4166 // 3. ->arrayofjomodescriptors
4167 EOarray *arrayofjomos = eo_array_New(4, sizeof(eOmc_jomo_descriptor_t), &data_mc->arrayofjomodescriptors);
4168 int numofjomos = mc_service.properties.numofjoints;
4169
4170 for(int i=0; i<numofjomos; i++)
4171 {
4172 eOmc_jomo_descriptor_t jomodes = {};
4173
4174 // 1. actuator is on pwm: we need the port
4175 jomodes.actuator.pwm.port = mc_service.properties.actuators[i].desc.pwm.port;
4176
4177 // 2. encoder1 is ...
4178 jomodes.encoder1.type = mc_service.properties.encoder1s[i].desc.type;
4179 jomodes.encoder1.port = mc_service.properties.encoder1s[i].desc.port;
4180 jomodes.encoder1.pos = mc_service.properties.encoder1s[i].desc.pos;
4181
4182 // 3. encoder2 is ...
4183 jomodes.encoder2.type = mc_service.properties.encoder2s[i].desc.type;
4184 jomodes.encoder2.port = mc_service.properties.encoder2s[i].desc.port;
4185 jomodes.encoder2.pos = mc_service.properties.encoder2s[i].desc.pos;
4186
4187 eo_array_PushBack(arrayofjomos, &jomodes);
4188
4189 }
4190
4191 // // 3. ->jomocoupling
4192 //eOmc_4jomo_coupling_t *jomocoupling = &data_mc->jomocoupling;
4193
4194 //ret = copyjomocouplingInfo(jomocoupling);
4195
4196 // ok, everything is done
4197 ret = true;
4198
4199 } break;
4200
4201 case eomn_serv_MC_mc4plusmais:
4202 {
4203 eOmn_serv_config_data_mc_mc4plusmais_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.mc4plusmais_based);
4204
4205 // 1. ->mais
4206 eOmn_serv_config_data_as_mais_t *mais = &data_mc->mais;
4207
4208 mais->canloc.port = mc_service.properties.maislocation.port;
4209 mais->canloc.addr = mc_service.properties.maislocation.addr;
4210 mais->canloc.insideindex = mc_service.properties.maislocation.insideindex;
4211
4212 mais->version.firmware.major = mc_service.properties.canboards.at(0).firmware.major;
4213 mais->version.firmware.minor = mc_service.properties.canboards.at(0).firmware.minor;
4214 mais->version.firmware.build = mc_service.properties.canboards.at(0).firmware.build;
4215 mais->version.protocol.major = mc_service.properties.canboards.at(0).protocol.major;
4216 mais->version.protocol.minor = mc_service.properties.canboards.at(0).protocol.minor;
4217
4218 // 2. ->arrayofjomodescriptors
4219 EOarray *arrayofjomos = eo_array_New(4, sizeof(eOmc_jomo_descriptor_t), &data_mc->arrayofjomodescriptors);
4220 int numofjomos = mc_service.properties.numofjoints;
4221
4222 for(int i=0; i<numofjomos; i++)
4223 {
4224 eOmc_jomo_descriptor_t jomodes = {};
4225
4226 // 1. actuator is on pwm: we need the port
4227 jomodes.actuator.pwm.port = mc_service.properties.actuators[i].desc.pwm.port;
4228
4229 // 2. encoder1 is ...
4230 jomodes.encoder1.type = mc_service.properties.encoder1s[i].desc.type;
4231 jomodes.encoder1.port = mc_service.properties.encoder1s[i].desc.port;
4232 jomodes.encoder1.pos = mc_service.properties.encoder1s[i].desc.pos;
4233
4234 // 3. encoder2 is ...
4235 jomodes.encoder2.type = mc_service.properties.encoder2s[i].desc.type;
4236 jomodes.encoder2.port = mc_service.properties.encoder2s[i].desc.port;
4237 jomodes.encoder2.pos = mc_service.properties.encoder2s[i].desc.pos;
4238
4239 eo_array_PushBack(arrayofjomos, &jomodes);
4240
4241 }
4242
4243
4245 //eOmc_4jomo_coupling_t *jomocoupling = &data_mc->jomocoupling;
4246
4247 //ret = copyjomocouplingInfo(jomocoupling);
4248
4249 // ok, everything is done
4250 ret = true;
4251
4252 } break;
4253
4254 case eomn_serv_MC_mc2pluspsc:
4255 {
4256 eOmn_serv_config_data_mc_mc2pluspsc_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.mc2pluspsc);
4257
4258 // 1. ->psc
4259 eOmn_serv_config_data_as_psc_t *psc = &data_mc->psc;
4260
4261
4262 for(size_t i=0; i<mc_service.properties.psclocations.size(); i++)
4263 {
4264 psc->boardInfo.canloc[i].port=mc_service.properties.psclocations[i].port;
4265 psc->boardInfo.canloc[i].addr=mc_service.properties.psclocations[i].addr;
4266 psc->boardInfo.canloc[i].insideindex=mc_service.properties.psclocations[i].insideindex;
4267 }
4268
4269
4270 psc->version.firmware.major = mc_service.properties.canboards.at(0).firmware.major;
4271 psc->version.firmware.minor = mc_service.properties.canboards.at(0).firmware.minor;
4272 psc->version.firmware.build = mc_service.properties.canboards.at(0).firmware.build;
4273 psc->version.protocol.major = mc_service.properties.canboards.at(0).protocol.major;
4274 psc->version.protocol.minor = mc_service.properties.canboards.at(0).protocol.minor;
4275
4276 // 2. ->arrayofjomodescriptors
4277 EOarray *arrayofjomos = eo_array_New(4, sizeof(eOmc_jomo_descriptor_t), &data_mc->arrayofjomodescriptors);
4278 int numofjomos = mc_service.properties.numofjoints;
4279
4280 for(int i=0; i<numofjomos; i++)
4281 {
4282 eOmc_jomo_descriptor_t jomodes = {};
4283
4284 // 1. actuator is on pwm: we need the port
4285 jomodes.actuator.pwm.port = mc_service.properties.actuators[i].desc.pwm.port;
4286
4287 // 2. encoder1 is ...
4288 jomodes.encoder1.type = mc_service.properties.encoder1s[i].desc.type;
4289 jomodes.encoder1.port = mc_service.properties.encoder1s[i].desc.port;
4290 jomodes.encoder1.pos = mc_service.properties.encoder1s[i].desc.pos;
4291
4292 // 3. encoder2 is ...
4293 jomodes.encoder2.type = mc_service.properties.encoder2s[i].desc.type;
4294 jomodes.encoder2.port = mc_service.properties.encoder2s[i].desc.port;
4295 jomodes.encoder2.pos = mc_service.properties.encoder2s[i].desc.pos;
4296
4297 eo_array_PushBack(arrayofjomos, &jomodes);
4298
4299 }
4300
4301 // ok, everything is done
4302 ret = true;
4303
4304 } break;
4305
4306
4307 case eomn_serv_MC_mc4plusfaps:
4308 {
4309 eOmn_serv_config_data_mc_mc4plusfaps_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.mc4plusfaps);
4310
4311 // 1. ->pos
4312 eOmn_serv_config_data_as_pos_t *pos = &data_mc->pos;
4313
4314 // get firmware and protocol info
4315 for(size_t b=0; b<eOas_pos_boards_maxnumber; b++)
4316 {
4317 pos->config.boardconfig[b].boardinfo.type = mc_service.properties.canboards[b].type;
4318 pos->config.boardconfig[b].boardinfo.firmware.major = mc_service.properties.canboards[b].firmware.major;
4319 pos->config.boardconfig[b].boardinfo.firmware.minor = mc_service.properties.canboards[b].firmware.minor;
4320 pos->config.boardconfig[b].boardinfo.firmware.build = mc_service.properties.canboards[b].firmware.build;
4321 pos->config.boardconfig[b].boardinfo.protocol.major = mc_service.properties.canboards[b].protocol.major;
4322 pos->config.boardconfig[b].boardinfo.protocol.minor = mc_service.properties.canboards[b].protocol.minor;
4323
4324 pos->config.boardconfig[b].canloc.addr = mc_service.properties.poslocations[b].addr;
4325 pos->config.boardconfig[b].canloc.port = mc_service.properties.poslocations[b].port;
4326
4327 for(size_t s=0; s<eOas_pos_sensorsinboard_maxnumber; s++)
4328 {
4329 pos->config.boardconfig[b].sensors[s].connector = s;
4330 pos->config.boardconfig[b].sensors[s].type = eoas_pos_TYPE_decideg;
4331 pos->config.boardconfig[b].sensors[s].port = static_cast<eObrd_portpos_t>(s);
4332 pos->config.boardconfig[b].sensors[s].enabled = 1;
4333 pos->config.boardconfig[b].sensors[s].invertdirection = 0;
4334 pos->config.boardconfig[b].sensors[s].rotation = eoas_pos_ROT_zero;
4335 pos->config.boardconfig[b].sensors[s].offset = 0;
4336 }
4337 }
4338
4339#if 0
4340 for(size_t i=0; i<mc_service.properties.poslocations.size(); i++)
4341 {
4342 pos->config.boardconfig[0].canloc.port = mc_service.properties.poslocations[i].port;
4343 pos->config.boardconfig[0].canloc.addr = mc_service.properties.poslocations[i].addr;
4344 pos->config.boardconfig[0].canloc.insideindex = mc_service.properties.poslocations[i].insideindex;
4345 }
4346
4347
4348 pos->config.boardconfig[0].boardinfo.firmware.major = mc_service.properties.canboards.at(0).firmware.major;
4349 pos->config.boardconfig[0].boardinfo.firmware.minor = mc_service.properties.canboards.at(0).firmware.minor;
4350 pos->config.boardconfig[0].boardinfo.firmware.build = mc_service.properties.canboards.at(0).firmware.build;
4351 pos->config.boardconfig[0].boardinfo.protocol.major = mc_service.properties.canboards.at(0).protocol.major;
4352 pos->config.boardconfig[0].boardinfo.protocol.minor = mc_service.properties.canboards.at(0).protocol.minor;
4353#endif
4354 // 2. ->arrayofjomodescriptors
4355 EOarray *arrayofjomos = eo_array_New(4, sizeof(eOmc_jomo_descriptor_t), &data_mc->arrayofjomodescriptors);
4356 size_t numofjomos = mc_service.properties.numofjoints;
4357
4358 for(size_t i=0; i<numofjomos; i++)
4359 {
4360 eOmc_jomo_descriptor_t jomodes = {};
4361
4362 // 1. actuator is on pwm: we need the port
4363 jomodes.actuator.pwm.port = mc_service.properties.actuators[i].desc.pwm.port;
4364
4365 // 2. encoder1 is ...
4366 jomodes.encoder1.type = mc_service.properties.encoder1s[i].desc.type;
4367 jomodes.encoder1.port = mc_service.properties.encoder1s[i].desc.port;
4368 jomodes.encoder1.pos = mc_service.properties.encoder1s[i].desc.pos;
4369
4370 // 3. encoder2 is ...
4371 jomodes.encoder2.type = mc_service.properties.encoder2s[i].desc.type;
4372 jomodes.encoder2.port = mc_service.properties.encoder2s[i].desc.port;
4373 jomodes.encoder2.pos = mc_service.properties.encoder2s[i].desc.pos;
4374
4375 eo_array_PushBack(arrayofjomos, &jomodes);
4376 }
4377
4378 // ok, everything is done
4379 ret = true;
4380
4381 } break;
4382
4383 case eomn_serv_MC_advfoc:
4384 {
4385 eOmn_serv_config_data_mc_advfoc_t *data_mc = &(mcconfig.ethservice.configuration.data.mc.advfoc);
4386
4387 ret = true;
4388
4389 // 1. ->eOmc_arrayof_4advjomodescriptors_t
4390 EOarray *arrayofjomos = eo_array_New(4, sizeof(eOmc_adv_jomo_descriptor_t), &data_mc->arrayof4advjomodescriptors);
4391 size_t numofjomos = mc_service.properties.numofjoints;
4392
4393 for(size_t i=0; i<numofjomos; i++)
4394 {
4395 eOmc_adv_jomo_descriptor_t jomodes = {};
4396
4397 // 1. actuator is on adv: we need the board, its location and its required versions of application and protocol
4398 if(mc_service.properties.actuators[i].type != eomc_act_advfoc)
4399 {
4400 yError() << "ServiceParser::parseService() unknown actuator value for eomn_serv_MC_advfoc mode. we need eomc_act_advfoc";
4401 ret = false;
4402 continue;
4403 }
4404
4405 // find the relevant brd inside the vector mc_service.properties.canboards that matches mc_service.properties.actuators[i].board
4406 // so far i just use the first one
4407
4408 // 1. actuator...
4409 jomodes.actuator.type = eomc_act_advfoc;
4410 jomodes.actuator.location = mc_service.properties.actuators[i].advdescr.location; //mc_service.properties.actuators[i].desc.gen.location;
4411 jomodes.actuator.board.type = mc_service.properties.actuators[i].advdescr.board.type;
4412 eObrd_firmwareversion_t fw {};
4413 eObrd_protocolversion_t pr {};
4414 // i must search for the fw and pr given the board inside ....
4415 bool ff {false};
4416 for(size_t i=0; i<mc_service.properties.canboards.size(); i++)
4417 {
4418 if(mc_service.properties.canboards[i].type == jomodes.actuator.board.type)
4419 {
4420 fw = mc_service.properties.canboards[i].firmware;
4421 pr = mc_service.properties.canboards[i].protocol;
4422 ff = true;
4423 break;
4424 }
4425 }
4426
4427 if(false == ff)
4428 {
4429 yError() << "ServiceParser::parseService() could not find the actuator board inside the mc_service.properties.canboards[] vector";
4430 return false;
4431 }
4432
4433 jomodes.actuator.board.firmware = fw;
4434 jomodes.actuator.board.protocol = pr;
4435
4436 // 2. encoder1 is ...
4437 jomodes.encoder1.type = mc_service.properties.encoder1s[i].desc.type;
4438 jomodes.encoder1.port = mc_service.properties.encoder1s[i].desc.port;
4439 jomodes.encoder1.pos = mc_service.properties.encoder1s[i].desc.pos;
4440
4441 // 3. encoder2 is ...
4442 jomodes.encoder2.type = mc_service.properties.encoder2s[i].desc.type;
4443 jomodes.encoder2.port = mc_service.properties.encoder2s[i].desc.port;
4444 jomodes.encoder2.pos = mc_service.properties.encoder2s[i].desc.pos;
4445
4446 eo_array_PushBack(arrayofjomos, &jomodes);
4447 }
4448
4449 // ok, everything is done
4450 ret = ret; // keep it as ret = ret ...
4451
4452 } break;
4453
4454 case eomn_serv_MC_generic:
4455 {
4456 yWarning() << "ServiceParser::parseService() eomn_serv_MC_generic detected. set type = eomn_serv_MC_generic to let the remote board configure itself according to its IP address";
4457 mcconfig.ethservice.configuration.type = eomn_serv_MC_generic;
4458 ret = true;
4459 } break;
4460
4461 default:
4462 {
4463 yError() << "ServiceParser::parseService() unknown value in eOmn_serv_type_t field";
4464 ret = false;
4465 } break;
4466 }
4467
4468
4469 return ret;
4470}
4471
4472
4474{
4475 if(mc_service.properties.encoder1s[index].desc.pos == eomc_pos_atjoint)
4476 {
4477 return(&mc_service.properties.encoder1s[index]);
4478 }
4479 else if(mc_service.properties.encoder2s[index].desc.pos == eomc_pos_atjoint)
4480 {
4481 return(&mc_service.properties.encoder2s[index]);
4482 }
4483 else
4484 return NULL;
4485}
4486
4488{
4489 if(mc_service.properties.encoder1s[index].desc.pos == eomc_pos_atmotor)
4490 {
4491 return(&mc_service.properties.encoder1s[index]);
4492 }
4493 else if(mc_service.properties.encoder2s[index].desc.pos == eomc_pos_atmotor)
4494 {
4495 return(&mc_service.properties.encoder2s[index]);
4496 }
4497 else
4498 return NULL;
4499
4500}
4501
4502//static eOmn_serv_configuration_t s_serv_config_mc_v3_0B0;
4503/*static const eOmn_serv_configuration_t s_serv_config_mc_v3_0B0 =
4504{ // eb12 or 0B0
4505 .type = eomn_serv_MC_mc4plus,
4506 .filler = {0},
4507 .data.mc.mc4plus_based =
4508 {
4509 .boardtype4mccontroller = emscontroller_board_HEAD_neckpitch_neckroll,
4510 .filler = {0},
4511 .arrayofjomodescriptors =
4512 {
4513 .head =
4514 {
4515 .capacity = 4,
4516 .itemsize = sizeof(eOmn_serv_jomo_descriptor_t),
4517 .size = 2,
4518 .internalmem = 0
4519 },
4520 .data =
4521 {
4522 { // joint 0: neck-pitch
4523 .actuator.pwm =
4524 {
4525 .port = 0 // eomn_serv_mc_port_mc4plus_pwmP3 is hal_motor1=0 ?? verify!
4526 },
4527 .sensor =
4528 {
4529 .type = eomc_enc_aea,
4530 .port = 1, // eomn_serv_mc_port_mc4plus_spiP11 ?? verify!
4531 .pos = eomc_pos_atjoint
4532 },
4533 .encoder2 =
4534 {
4535 .type = eomc_enc_qenc,
4536 .port = 0, // eomn_serv_mc_port_mc4plus_qencP3 ?? verify!
4537 .pos = eomc_pos_atmotor
4538 }
4539 },
4540 { // joint 1: neck-roll
4541 .actuator.pwm =
4542 {
4543 .port = 2 // eomn_serv_mc_port_mc4plus_pwmP4 is hal_motor3=2 ?? verify!
4544 },
4545 .sensor =
4546 {
4547 .type = eomc_enc_aea,
4548 .port = 0, // eomn_serv_mc_port_mc4plus_spiP10 ?? verify!
4549 .pos = eomc_pos_atjoint
4550 },
4551 .encoder2 =
4552 {
4553 .type = eomc_enc_qenc,
4554 .port = 2, // eomn_serv_mc_port_mc4plus_qencP4 ?? verify!
4555 .pos = eomc_pos_atmotor
4556 }
4557 },
4558 { // joint 2
4559 .actuator.pwm =
4560 {
4561 .port = eomn_serv_mc_port_none
4562 },
4563 .sensor =
4564 {
4565 .type = eomn_serv_mc_sensor_none,
4566 .port = eomn_serv_mc_port_none,
4567 .pos = eomn_serv_mc_sensor_pos_none
4568 },
4569 .encoder2 =
4570 {
4571 .type = eomn_serv_mc_sensor_none,
4572 .port = eomn_serv_mc_port_none,
4573 .pos = eomn_serv_mc_sensor_pos_none
4574 }
4575 },
4576 { // joint 3
4577 .actuator.pwm =
4578 {
4579 .port = eomn_serv_mc_port_none
4580 },
4581 .sensor =
4582 {
4583 .type = eomn_serv_mc_sensor_none,
4584 .port = eomn_serv_mc_port_none,
4585 .pos = eomn_serv_mc_sensor_pos_none
4586 },
4587 .encoder2 =
4588 {
4589 .type = eomn_serv_mc_sensor_none,
4590 .port = eomn_serv_mc_port_none,
4591 .pos = eomn_serv_mc_sensor_pos_none
4592 }
4593 }
4594 }
4595 },
4596 .jomocoupling =
4597 {
4598 .joint2set =
4599 {
4600 eomc_jointSetNum_zero, eomc_jointSetNum_zero, eomc_jointSetNum_none, eomc_jointSetNum_none
4601 },
4602 .joint2motor =
4603 { // zero matrix: use matrix embedded in controller and seecetd by boardtype4mccontroller
4604 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4605 { EO_COMMON_FLOAT_TO_Q17_14(-1.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4606 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4607 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4608 },
4609 .encoder2joint =
4610 { // identical matrix
4611 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4612 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4613 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4614 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4615 }
4616 }
4617 }
4618};
4619*/
4620//static eOmn_serv_configuration_t s_serv_config_mc_v3_0B9;
4621/*static const eOmn_serv_configuration_t s_serv_config_mc_v3_0B9=
4622{ // eb15 or 0B9
4623 .type = eomn_serv_MC_mc4plus,
4624 .filler = {0},
4625 .data.mc.mc4plus_based =
4626 {
4627 .boardtype4mccontroller = emscontroller_board_4jointsNotCoupled,
4628 .filler = {0},
4629 .arrayofjomodescriptors =
4630 {
4631 .head =
4632 {
4633 .capacity = 4,
4634 .itemsize = sizeof(eOmn_serv_jomo_descriptor_t),
4635 .size = 4,
4636 .internalmem = 0
4637 },
4638 .data =
4639 {
4640 { // joint 0: lip-left
4641 .actuator.pwm =
4642 {
4643 .port = 2 // eomn_serv_mc_port_mc4plus_pwmP4 is hal_motor2=1 ?? verify!
4644 },
4645 .sensor =
4646 {
4647 .type = eomc_enc_qenc,
4648 .port = 2, // eomn_serv_mc_port_mc4plus_qencP4 ?? verify!
4649 .pos = eomc_pos_atjoint
4650 },
4651 .encoder2 =
4652 {
4653 .type = eomc_enc_qenc,
4654 .port = 2, // eomn_serv_mc_port_mc4plus_qencP4 ?? verify!
4655 .pos = eomc_pos_atmotor
4656 }
4657 },
4658 { // joint 1: lip-high
4659 .actuator.pwm =
4660 {
4661 .port = 1 // eomn_serv_mc_port_mc4plus_pwmP2 is hal_motor2=1 ?? verify!
4662 },
4663 .sensor =
4664 {
4665 .type = eomc_enc_qenc,
4666 .port = 1, // eomn_serv_mc_port_mc4plus_qencP2 ?? verify!
4667 .pos = eomc_pos_atjoint
4668 },
4669 .encoder2 =
4670 {
4671 .type = eomc_enc_qenc,
4672 .port = 1, // eomn_serv_mc_port_mc4plus_qencP2 ?? verify!
4673 .pos = eomc_pos_atmotor
4674 }
4675 },
4676 { // joint 2: lip-right
4677 .actuator.pwm =
4678 {
4679 .port = 0 // eomn_serv_mc_port_mc4plus_pwmP3 is hal_motor4=3 ?? verify!
4680 },
4681 .sensor =
4682 {
4683 .type = eomc_enc_qenc,
4684 .port = 0, // eomn_serv_mc_port_mc4plus_qencP3 is hal_quad_enc1 = 0 ?? verify!
4685 .pos = eomc_pos_atjoint
4686 },
4687 .encoder2 =
4688 {
4689 .type = eomc_enc_qenc,
4690 .port = 0, // eomn_serv_mc_port_mc4plus_qencP3 is hal_quad_enc1 = 0 ?? verify!
4691 .pos = eomc_pos_atmotor
4692 }
4693 },
4694 { // joint 3: lip-bottom
4695 .actuator.pwm =
4696 {
4697 .port = 3 // eomn_serv_mc_port_mc4plus_pwmP5 is hal_motor3=2 ?? verify!
4698 },
4699 .sensor =
4700 {
4701 .type = eomc_enc_qenc,
4702 .port = 3, // eomn_serv_mc_port_mc4plus_qencP5 is hal_quad_enc4 = 3 ?? verify!
4703 .pos = eomc_pos_atjoint
4704 },
4705 .encoder2 =
4706 {
4707 .type = eomc_enc_qenc,
4708 .port = 3, // eomn_serv_mc_port_mc4plus_qencP5 is hal_quad_enc4 = 3 ?? verify!
4709 .pos = eomc_pos_atmotor
4710 }
4711 }
4712 }
4713 },
4714 .jomocoupling =
4715 {
4716 .joint2set =
4717 { // each joint is on a different set
4718 0, 1, 2, 3
4719 },
4720 .joint2motor =
4721 { // zero matrix: use matrix embedded in controller and seecetd by boardtype4mccontroller
4722 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4723 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4724 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4725 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) }
4726 },
4727 .encoder2joint =
4728 { // identical matrix
4729 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4730 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4731 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4732 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4733 }
4734 }
4735 }
4736};*/
4737
4738
4739
4740
4741// static eOmn_serv_configuration_t s_serv_config_mc_v3_0B1 = {};
4742/*static const eOmn_serv_configuration_t s_serv_config_mc_v3_0B1 =
4743{ // eb13 or 0B1
4744 .type = eomn_serv_MC_mc4plus,
4745 .filler = {0},
4746 .data.mc.mc4plus_based =
4747 {
4748 .boardtype4mccontroller = emscontroller_board_HEAD_neckyaw_eyes,
4749 .filler = {0},
4750 .arrayofjomodescriptors =
4751 {
4752 .head =
4753 {
4754 .capacity = 4,
4755 .itemsize = sizeof(eOmn_serv_jomo_descriptor_t),
4756 .size = 4,
4757 .internalmem = 0
4758 },
4759 .data =
4760 {
4761 { // joint 0: neck-yaw
4762 .actuator.pwm =
4763 {
4764 .port = 0 // eomn_serv_mc_port_mc4plus_pwmP3 is hal_motor1=0 ?? verify!
4765 },
4766 .sensor =
4767 {
4768 .type = eomc_enc_aea,
4769 .port = 1, // eomn_serv_mc_port_mc4plus_spiP11 ?? verify!
4770 .pos = eomc_pos_atjoint
4771 },
4772 .encoder2 =
4773 {
4774 .type = eomc_enc_qenc,
4775 .port = 0, // eomn_serv_mc_port_mc4plus_qencP3 ?? verify!
4776 .pos = eomc_pos_atmotor
4777 }
4778 },
4779 { // joint 1: eyes-tilt
4780 .actuator.pwm =
4781 {
4782 .port = 1 // eomn_serv_mc_port_mc4plus_pwmP2 is hal_motor2=1 ?? verify!
4783 },
4784 .sensor =
4785 {
4786 .type = eomc_enc_aea,
4787 .port = 0, // eomn_serv_mc_port_mc4plus_spiP10 ?? verify!
4788 .pos = eomc_pos_atjoint
4789 },
4790 .encoder2 =
4791 {
4792 .type = eomc_enc_qenc,
4793 .port = 1, // eomn_serv_mc_port_mc4plus_qencP2 ?? verify!
4794 .pos = eomc_pos_atmotor
4795 }
4796 },
4797 { // joint 2: right-eye
4798 .actuator.pwm =
4799 {
4800 .port = 3 // eomn_serv_mc_port_mc4plus_pwmP5 is hal_motor4=3 ?? verify!
4801 },
4802 .sensor =
4803 {
4804 .type = eomc_enc_qenc,
4805 .port = 3, // eomn_serv_mc_port_mc4plus_qencP5 is hal_quad_enc4 = 3 ?? verify!
4806 .pos = eomc_pos_atjoint
4807 },
4808 .encoder2 =
4809 {
4810 .type = eomc_enc_qenc,
4811 .port = 3, // eomn_serv_mc_port_mc4plus_qencP5 is hal_quad_enc4 = 3 ?? verify!
4812 .pos = eomc_pos_atmotor
4813 }
4814 },
4815 { // joint 3: left-eye
4816 .actuator.pwm =
4817 {
4818 .port = 2 // eomn_serv_mc_port_mc4plus_pwmP4 is hal_motor3=2 ?? verify!
4819 },
4820 .sensor =
4821 {
4822 .type = eomc_enc_qenc,
4823 .port = 2, // eomn_serv_mc_port_mc4plus_qencP4 is hal_quad_enc3 = 2 ?? verify!
4824 .pos = eomc_pos_atjoint
4825 },
4826 .encoder2 =
4827 {
4828 .type = eomc_enc_qenc,
4829 .port = 2, // eomn_serv_mc_port_mc4plus_qencP4 is hal_quad_enc3 = 2 ?? verify!
4830 .pos = eomc_pos_atmotor
4831 }
4832 }
4833 }
4834 },
4835 .jomocoupling =
4836 {
4837 .joint2set =
4838 { //joint 2 and 3 are coupled
4839 eomc_jointSetNum_zero, eomc_jointSetNum_one, eomc_jointSetNum_two, eomc_jointSetNum_two
4840 },
4841
4842 //inverted matrix: joint to motor
4843 // |m0| | 1 0 0 0 | |j0|
4844 // |m1| = | 0 1 0 0 | * |j1|
4845 // |m2| | 0 0 1 -1 | |j2|
4846 // |m3| | 0 0 1 1 | |j2|
4847
4848
4849 .joint2motor =
4850 { // zero matrix: use matrix embedded in controller and seecetd by boardtype4mccontroller
4851 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4852 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4853 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(-1.0f) },
4854 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4855 },
4856 .encoder2joint =
4857 { // identical matrix
4858 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4859 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4860 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4861 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4862 }
4863 }
4864 }
4865};
4866*/
4867//static eOmn_serv_configuration_t s_serv_config_mc_v3_0B7;
4868/*static const eOmn_serv_configuration_t s_serv_config_mc_v3_0B7 =
4869{ // eb14 or 0B7f
4870 .type = eomn_serv_MC_mc4plus,
4871 .filler = {0},
4872 .data.mc.mc4plus_based =
4873 {
4874 .boardtype4mccontroller = emscontroller_board_FACE_eyelids_jaw,
4875 .filler = {0},
4876 .arrayofjomodescriptors =
4877 {
4878 .head =
4879 {
4880 .capacity = 4,
4881 .itemsize = sizeof(eOmn_serv_jomo_descriptor_t),
4882 .size = 2,
4883 .internalmem = 0
4884 },
4885 .data =
4886 {
4887 { // joint 0: jaw
4888 .actuator.pwm =
4889 {
4890 ret = ret; .port = 0 // eomn_serv_mc_port_mc4plus_pwmP3 is hal_motor1=0 ?? verify!
4891 },
4892 .sensor =
4893 {
4894 .type = eomc_enc_aea,
4895 .port = 1, // eomn_serv_mc_port_mc4plus_spiP11 ?? verify!
4896 .pos = eomc_pos_atjoint
4897 },
4898 .encoder2 =
4899 {
4900 .type = eomn_serv_mc_sensor_none,
4901 .port = eomn_serv_mc_port_none,
4902 .pos = eomn_serv_mc_sensor_pos_none
4903 }
4904 },
4905 { // joint 1: eyelids
4906 .actuator.pwm =
4907 {
4908 .port = 1 // eomn_serv_mc_port_mc4plus_pwmP2 is hal_motor2=1 ?? verify!
4909 },
4910 .sensor =
4911 {
4912 .type = eomc_enc_aea,
4913 .port = 0, // eomn_serv_mc_port_mc4plus_spiP10 ?? verify!
4914 .pos = eomc_pos_atjoint
4915 },
4916 .encoder2 =
4917 {
4918 .type = eomc_enc_qenc,
4919 .port = 1, // eomn_serv_mc_port_mc4plus_qencP2 ?? verify!
4920 .pos = eomc_pos_atmotor
4921 }
4922 },
4923 { // joint 2
4924 .actuator.pwm =
4925 {
4926 .port = eomn_serv_mc_port_none
4927 },
4928 .sensor =
4929 {
4930 .type = eomn_serv_mc_sensor_none,
4931 .port = eomn_serv_mc_port_none,
4932 .pos = eomn_serv_mc_sensor_pos_none
4933 },
4934 .encoder2 =
4935 {
4936 .type = eomn_serv_mc_sensor_none,
4937 .port = eomn_serv_mc_port_none,
4938 .pos = eomn_serv_mc_sensor_pos_none
4939 }
4940 },
4941 { // joint 3
4942 .actuator.pwm =
4943 {
4944 .port = eomn_serv_mc_port_none
4945 },
4946 .sensor =
4947 {
4948 .type = eomn_serv_mc_sensor_none,
4949 .port = eomn_serv_mc_port_none,
4950 .pos = eomn_serv_mc_sensor_pos_none
4951 },
4952 .encoder2 =
4953 {
4954 .type = eomn_serv_mc_sensor_none,
4955 .port = eomn_serv_mc_port_none,
4956 .pos = eomn_serv_mc_sensor_pos_none
4957 }
4958 }
4959 }
4960 },
4961 .jomocoupling =
4962 {
4963 .joint2set =
4964 { // each joint is on a different set
4965 eomc_jointSetNum_zero, eomc_jointSetNum_one, eomc_jointSetNum_none, eomc_jointSetNum_none
4966 },
4967 .joint2motor =
4968 { // zero matrix: use matrix embedded in controller and seecetd by boardtype4mccontroller
4969 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4970 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4971 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4972 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4973 },
4974 .encoder2joint =
4975 { // identical matrix
4976 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4977 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4978 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
4979 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
4980 }
4981 }
4982 }
4983};
4984*/
4985
4986/*eOmn_serv_configuration_t* arrayConf[4] =
4987{
4988 &s_serv_config_mc_v3_0B9, // board ip.1, 0b9, face 4 lips
4989 &s_serv_config_mc_v3_0B7, // board ip.2, 0b7, face eyelids + jaw
4990 &s_serv_config_mc_v3_0B1, // board ip.3, 0b1, head neck yaw + 3 eyes
4991 &s_serv_config_mc_v3_0B0
4992}*/
4993
4994static eOmn_serv_configuration_t s_serv_config_mc_v3_0B1 = {};
4995
4996bool ServiceParser::parseService2(Searchable &config, servConfigMC_t &mcconfig)
4997{
4998 eOmc_arrayof_4jomodescriptors_t *ja = &s_serv_config_mc_v3_0B1.data.mc.mc4plus_based.arrayofjomodescriptors;
4999 eOmc_4jomo_coupling_t *jc = &s_serv_config_mc_v3_0B1.data.mc.mc4plus_based.jomocoupling;
5000
5001
5002 eOq17_14_t m1[][4] =
5003 { // zero matrix: use matrix embedded in controller and seecetd by boardtype4mccontroller
5004 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5005 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5006 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(-1.0f) },
5007 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
5008 };
5009
5010 eOq17_14_t m2[][4]=
5011 { // identical matrix
5012 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5013 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5014 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5015 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
5016 };
5017
5018
5019 //s_serv_config_mc_v3_0B1.type = eomn_serv_MC_mc4plus;
5020 //s_serv_config_mc_v3_0B1.filler = {0, 0, 0};
5021
5022 //s_serv_config_mc_v3_0B1.data.mc.mc4plus_based.boardtype4mccontroller = 6; //emscontroller_board_HEAD_neckyaw_eyes;
5023 //s_serv_config_mc_v3_0B1.data.mc.mc4plus_based.filler = {0};
5024
5025 ja->head.capacity = 4;
5026 ja->head.itemsize = sizeof(eOmc_jomo_descriptor_t);
5027 ja->head.size = 4;
5028 ja->head.internalmem = 0;
5029
5030 ja->data[0].actuator.pwm.port = 0 ; // eomn_serv_mc_port_mc4plus_pwmP3 is hal_motor1=0 ?? verify!
5031 ja->data[0].encoder1.type = eomc_enc_aea;
5032 ja->data[0].encoder1.port = 1; // eomn_serv_mc_port_mc4plus_spiP11 ?? verify!
5033 ja->data[0].encoder1.pos = eomc_pos_atjoint;
5034
5035 ja->data[0].encoder2.type = eomc_enc_qenc;
5036 ja->data[0].encoder2.port = 0; // eomn_serv_mc_port_mc4plus_qencP3 ?? verify!
5037 ja->data[0].encoder2.pos = eomc_pos_atmotor;
5038
5039 ja->data[1].actuator.pwm.port = 1; // eomn_serv_mc_port_mc4plus_pwmP2 is hal_motor2=1 ?? verify!
5040 ja->data[1].encoder1.type = eomc_enc_aea;
5041 ja->data[1].encoder1.port = 0; // eomn_serv_mc_port_mc4plus_spiP10 ?? verify!
5042 ja->data[1].encoder1.pos = eomc_pos_atjoint;
5043 ja->data[1].encoder2.type = eomc_enc_qenc;
5044 ja->data[1].encoder2.port = 1; // eomn_serv_mc_port_mc4plus_qencP2 ?? verify!
5045 ja->data[1].encoder2.pos = eomc_pos_atmotor;
5046
5047 ja->data[2].actuator.pwm.port = 3;
5048 ja->data[2].encoder1.type = eomc_enc_qenc;
5049 ja->data[2].encoder1.port = 3; // eomn_serv_mc_port_mc4plus_qencP5 is hal_quad_enc4 = 3 ?? verify!
5050 ja->data[2].encoder1.pos = eomc_pos_atjoint;
5051 ja->data[2].encoder2.type = eomc_enc_qenc,
5052 ja->data[2].encoder2.port = 3, // eomn_serv_mc_port_mc4plus_qencP5 is hal_quad_enc4 = 3 ?? verify!
5053 ja->data[2].encoder2.pos = eomc_pos_atmotor;
5054
5055 ja->data[3].actuator.pwm.port = 2;
5056
5057 ja->data[3].encoder1.type = eomc_enc_qenc;
5058 ja->data[3].encoder1.port = 2; // eomn_serv_mc_port_mc4plus_qencP4 is hal_quad_enc3 = 2 ?? verify!
5059 ja->data[3].encoder1.pos = eomc_pos_atjoint;
5060
5061
5062 ja->data[3].encoder2.type = eomc_enc_qenc;
5063 ja->data[3].encoder2.port = 2; // eomn_serv_mc_port_mc4plus_qencP4 is hal_quad_enc3 = 2 ?? verify!
5064 ja->data[3].encoder2.pos = eomc_pos_atmotor;
5065
5066
5067 jc->joint2set[0] = eomc_jointSetNum_zero;
5068 jc->joint2set[1] = eomc_jointSetNum_one;
5069 jc->joint2set[2] = eomc_jointSetNum_two;
5070 jc->joint2set[3] = eomc_jointSetNum_two;
5071
5072
5073/*
5074 jc->joint2motor =
5075 { // zero matrix: use matrix embedded in controller and seecetd by boardtype4mccontroller
5076 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5077 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5078 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(-1.0f) },
5079 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
5080 };
5081 jc->encoder2joint =
5082 { // identical matrix
5083 { EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5084 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5085 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f) },
5086 { EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(0.0f), EO_COMMON_FLOAT_TO_Q17_14(1.0f) }
5087 };
5088
5089
5090
5091*/
5092
5093 memcpy(&jc->joint2motor, &m1, sizeof(m1));
5094 memcpy(&jc->encoder2joint, &m2, sizeof(m2));
5095
5096 yError() << "print first m ";
5097 for(int r=0; r<4; r++)
5098 {
5099 for(int c=0; c<4; c++)
5100 {
5101 yError() << "r=" <<r << "c=" << c << "val=" << m1[r][c];
5102 }
5103 }
5104
5105 yError() << "print second m ";
5106 for(int r=0; r<4; r++)
5107 {
5108 for(int c=0; c<4; c++)
5109 {
5110 yError() << "r=" <<r << "c=" << c << "val=" << m2[r][c];
5111 }
5112 }
5113
5114
5115
5116 if(mcconfig.id > 3)
5117 {
5118 yError() << " id scheda sbagliato " << mcconfig.id;
5119 return false;
5120 }
5121
5122
5123 memcpy(&mcconfig.ethservice, &s_serv_config_mc_v3_0B1, sizeof(eOmn_serv_configuration_t));
5124 return true;
5125}
5126
5127#endif // #if defined(SERVICE_PARSER_USE_MC)
5128
5129// eof
bool parseService2(yarp::os::Searchable &config, servConfigMC_t &mcconfig)
bool parse_encoder_port(std::string const &fromstring, eObrd_ethtype_t const ethboard, eOmc_encoder_t type, uint8_t &toport, bool &formaterror)
bool parse_port_conn(std::string const &fromstring, eObrd_type_t const board, uint8_t &toport, bool &formaterror)
servASstrainSettings_t as_strain_settings
bool parse_actuator_port(std::string const &fromstring, eObrd_ethtype_t const ethboard, eOmc_actuator_t const type, eOmc_actuator_descriptor_t &todes, bool &formaterror)
bool parse_POS_CALIB_rotation(std::string const &fromstring, eoas_pos_ROT_t &rot, bool &formaterror)
bool convert(std::string const &fromstring, eOmc_actuator_t &toactuatortype, bool &formaterror)
servMC_encoder_t * getEncoderAtMotor(int index)
bool parse_mais(std::string const &fromstring, eObrd_portmais_t &pmais, bool &formaterror)
servMCcollector_t mc_service
eOmn_serv_config_data_sk_skin_t tmp
servSKcollector_t sk_service
bool parse_port_psc(std::string const &fromstring, uint8_t &toport, bool &formaterror)
bool parse_POS_CALIB_type(std::string const &fromstring, eoas_pos_TYPE_t &type, bool &formaterror)
bool parseService(yarp::os::Searchable &config, servConfigMais_t &maisconfig)
bool parse_port_pos(std::string const &fromstring, uint8_t &toport, bool &formaterror)
bool parse_POS_connector(std::string const &fromstring, const eObrd_type_t brd, eObrd_connector_t &conn, bool &formaterror)
bool parse_POS_port(std::string const &fromstring, eObrd_portpos_t &ppos, bool &formaterror)
bool parse_connector(const std::string &fromstring, eObrd_connector_t &toconnector, bool &formaterror)
servMC_encoder_t * getEncoderAtJoint(int index)
bool parse_psc(std::string const &fromstring, eObrd_portpsc_t &ppsc, bool &formaterror)
servAScollector_t as_service
bool parse_port_mais(std::string const &fromstring, uint8_t &toport, bool &formaterror)
uint8_t board
int n
Copyright (C) 2008 RobotCub Consortium.
eOmn_serv_type_t type
servASsettings_t settings
servASproperties_t properties
std::vector< servAnalogSensor_t > sensors
std::vector< servCanBoard_t > canboards
std::vector< servAnalogSensor_t > enabledsensors
uint16_t acquisitionrate
servAnalogPOScalibration_t calibration
eObrd_connector_t connector
servAnalogPOSspecific_t pos
std::string frameName
eObrd_type_t boardtype
std::string sensorName
eObrd_location_t location
eOas_sensor_t type
eObrd_cantype_t type
eObrd_protocolversion_t protocol
eObrd_firmwareversion_t firmware
std::string nameOfStrain
eOmn_serv_parameter_t ethservice
eOmn_serv_parameter_t ethservice
std::vector< eOas_inertial3_descriptor_t > inertials
std::vector< std::string > id
std::vector< std::string > sensorName
eOmn_serv_parameter_t ethservice
eOmn_serv_parameter_t ethservice
std::string nameOfMais
eOmn_serv_parameter_t ethservice
eOmn_serv_parameter_t ethservice
servCanBoard_t canboard
eOmn_serv_parameter_t ethservice
std::string nameOfStrain
eOmc_adv_actuator_descriptor_t advdescr
eOmc_actuator_descriptor_t desc
eOmc_actuator_t type
eOmc_encoder_descriptor_t desc
servMCproperties_t properties
eOmn_serv_diagn_cfg_t diagconfig
eOmn_serv_type_t type
std::vector< eOmc_mc4broadcast_t > mc4broadcasts
eOmc_mc4shifts_t mc4shifts
std::vector< eObrd_canlocation_t > poslocations
eObrd_canlocation_t maislocation
std::vector< servMC_actuator_t > actuators
std::vector< servMC_encoder_t > encoder2s
eObrd_ethtype_t ethboardtype
std::vector< eObrd_canlocation_t > mc4joints
std::vector< servMC_encoder_t > encoder1s
std::vector< eObrd_canlocation_t > psclocations
std::vector< servCanBoard_t > canboards
eOmn_serv_type_t type
servSKproperties_t properties
servCanBoard_t canboard