Revision 9461fadc

View differences:

modules/DiWheelDrive_1-1/chconf.h
64 64
 *          this value.
65 65
 */
66 66
#if (AMIROOS_CFG_TESTS_ENABLE != true) || defined(__DOXYGEN__)
67
#define CH_CFG_ST_TIMEDELTA                 10
67
#define CH_CFG_ST_TIMEDELTA                 20
68 68
#else
69 69
#define CH_CFG_ST_TIMEDELTA                 2
70 70
#endif
modules/DiWheelDrive_1-1/module.h
456 456
 */
457 457
#define MODULE_SSSP_EVENTFLAGS_UP               MODULE_OS_IOEVENTFLAGS_SYSUARTUP
458 458

  
459
/**
460
 * @brief   Hook to handle IO events during SSSP startup synchronization.
461
 */
462
#define MODULE_SSSP_STARTUP_2_2_IOEVENT_HOOK(mask, flags) {                   \
463
  /* ignore all events */                                                     \
464
  (void)mask;                                                                 \
465
  (void)flags;                                                                \
466
}
467

  
468 459
/** @} */
469 460

  
470 461
/*===========================================================================*/
modules/LightRing_1-0/chconf.h
64 64
 *          this value.
65 65
 */
66 66
#if (AMIROOS_CFG_TESTS_ENABLE != true) || defined(__DOXYGEN__)
67
#define CH_CFG_ST_TIMEDELTA                 10
67
#define CH_CFG_ST_TIMEDELTA                 20
68 68
#else
69 69
#define CH_CFG_ST_TIMEDELTA                 2
70 70
#endif
modules/LightRing_1-0/module.h
296 296
 */
297 297
#define MODULE_SSSP_EVENTFLAGS_DN               MODULE_OS_IOEVENTFLAGS_SYSUARTDN
298 298

  
299
/**
300
 * @brief   Hook to handle IO events during SSSP startup synchronization.
301
 */
302
#define MODULE_SSSP_STARTUP_2_2_IOEVENT_HOOK(mask, flags) {                   \
303
  /* ignore all events */                                                     \
304
  (void)mask;                                                                 \
305
  (void)flags;                                                                \
306
}
307

  
308 299
/** @} */
309 300

  
310 301
/*===========================================================================*/
modules/PowerManagement_1-1/chconf.h
59 59
 *          The value one is not valid, timeouts are rounded up to
60 60
 *          this value.
61 61
 */
62
#define CH_CFG_ST_TIMEDELTA                 10
62
#define CH_CFG_ST_TIMEDELTA                 20
63 63

  
64 64
/** @} */
65 65

  
modules/PowerManagement_1-1/module.h
543 543
 */
544 544
#define MODULE_SSSP_EVENTFLAGS_DN               MODULE_OS_IOEVENTFLAGS_SYSUARTDN
545 545

  
546
/**
547
 * @brief   Hook to handle IO events during SSSP startup synchronization.
548
 */
549
#define MODULE_SSSP_STARTUP_2_2_IOEVENT_HOOK(mask, flags) {                   \
550
  /* ignore all events */                                                     \
551
  (void)mask;                                                                 \
552
  (void)flags;                                                                \
553
}
554

  
555 546
/** @} */
556 547

  
557 548
/*===========================================================================*/
os/core/src/aos_main.cpp
67 67
#define SSSP_STACKINIT_CANMSGID_ABORT           0x001
68 68

  
69 69
/**
70
 * @brief   CAN message identifier for calender synchronization message.
71
 */
72
#define CALENDERSYNC_CANMSGID                   0x004
73

  
74
/**
70 75
 * @brief   Listener object for I/O events.
71 76
 */
72 77
static event_listener_t _eventListenerIO;
......
130 135
}
131 136

  
132 137
/**
133
 * @brief   Helper function to serialize 32 bit data.
138
 * @brief   Helper function to serialize data.
134 139
 *
135 140
 * @param[out]  dst   Pointer to the output buffer.
136
 * @param[in]   src   32 bit data to be serielized.
141
 * @param[in]   src   Data to be serialized.
142
 * @param[in]   n     Number of bytes to serialize.
137 143
 */
138
inline void _canSerialize32(uint8_t* dst, const uint32_t src)
144
inline void _serialize(uint8_t* dst, const uint64_t src, const uint8_t n)
139 145
{
140 146
  aosDbgCheck(dst != NULL);
147
  aosDbgCheck(n > 0 && n <= 8);
141 148

  
142
  for (uint8_t byte = 0; byte < 4; ++byte) {
149
  for (uint8_t byte = 0; byte < n; ++byte) {
143 150
    dst[byte] = (uint8_t)((src >> (byte * 8)) & 0xFF);
144 151
  }
145 152

  
......
147 154
}
148 155

  
149 156
/**
150
 * @brief   Helper function to deserialize 32 bit data.
157
 * @brief   Helper function to deserialize data.
151 158
 *
152 159
 * @param[in] src   Pointer to the buffer of data to be deserialzed.
160
 * @param[in] n     Number of bytes to deserialize.
153 161
 *
154 162
 * @return    The deserialized 32 bit data.
155 163
 */
156
inline uint32_t _canDeserialize32(uint8_t* src)
164
inline uint64_t _deserialize(uint8_t* src, const uint8_t n)
157 165
{
158 166
  aosDbgCheck(src != NULL);
167
  aosDbgCheck(n > 0 && n <= 8);
159 168

  
160
  return ((uint32_t)src[0]) | (((uint32_t)src[1]) << 8) | (((uint32_t)src[2]) << 16) | (((uint32_t)src[3]) << 24);
169
  uint64_t result = 0;
170
  for (uint8_t byte = 0; byte < n; ++byte) {
171
    result |= ((uint64_t)src[byte]) << (byte * 8);
172
  }
173

  
174
  return result;
175
}
176

  
177
/**
178
 * @brief   Converter function to encode a TM value to a single unsigned 64 bit integer.
179
 *
180
 * @details Contents of the TM struct are mapped as follows:
181
 *            bits  |63     62|61      53|52    50|49         26|25     22|21     17|16     12|11      6|5       0|
182
 *            #bits |       2 |        9 |      3 |          24 |       4 |       5 |       5 |       6 |       6 |
183
 *            value |   isdst |     yday |   wday |        year |     mon |    mday |    hour |     min |     sec |
184
 *            range | special | [0, 365] | [0, 6] | [1900, ...] | [0, 11] | [1, 31] | [0, 23] | [0, 59] | [0, 61] |
185
 *          The Daylight Saving Time Flag (isdsst) is encoded as follows:
186
 *            DST not in effect         -> 0
187
 *            DST in effect             -> 1
188
 *            no information available  -> 2
189
 *
190
 * @param[in] src   Pointer to the TM struct to encode.
191
 *
192
 * @return  An unsigned 64 bit integer, which holds the encoded time value.
193
 */
194
inline uint64_t _TM2U64(struct tm* src)
195
{
196
  aosDbgCheck(src != NULL);
197

  
198
  return (((uint64_t)(src->tm_sec  & 0x0000003F) << (0))               |
199
          ((uint64_t)(src->tm_min  & 0x0000003F) << (6))               |
200
          ((uint64_t)(src->tm_hour & 0x0000001F) << (12))              |
201
          ((uint64_t)(src->tm_mday & 0x0000001F) << (17))              |
202
          ((uint64_t)(src->tm_mon  & 0x0000000F) << (22))              |
203
          ((uint64_t)(src->tm_year & 0x00FFFFFF) << (26))              |
204
          ((uint64_t)(src->tm_wday & 0x00000007) << (50))              |
205
          ((uint64_t)(src->tm_yday & 0x000001FF) << (53))              |
206
          ((uint64_t)((src->tm_isdst == 0) ? 0 : (src->tm_isdst > 0) ? 1 : 2) << (62)));
207
}
208

  
209
/**
210
 * @brief   Converter functiomn to retrieve the encoded TM value from an unsigned 64 bit integer.
211
 *
212
 * @details For information on the encoding, please refer to @p _TM2U64 function.
213
 *
214
 * @param[out] dst  The TM struct to fill with the decoded values.
215
 * @param[in]  src  Unsigned 64 bit integer holding the encoded TM value.
216
 */
217
inline void _U642TM(struct tm* dst, const uint64_t src)
218
{
219
  aosDbgCheck(dst != NULL);
220

  
221
  dst->tm_sec  = (src >> 0)  & 0x0000003F;
222
  dst->tm_min  = (src >> 6)  & 0x0000003F;
223
  dst->tm_hour = (src >> 12) & 0x0000001F;
224
  dst->tm_mday = (src >> 17) & 0x0000001F;
225
  dst->tm_mon  = (src >> 22) & 0x0000000F;
226
  dst->tm_year = (src >> 26) & 0x00FFFFFF;
227
  dst->tm_wday = (src >> 50) & 0x00000007;
228
  dst->tm_yday = (src >> 53) & 0x000001FF;
229
  dst->tm_isdst = (((src >> 62) & 0x03) == 0) ? 0 : (((src >> 62) & 0x03) > 0) ? 1 : -1;
230

  
231
  return;
161 232
}
162 233

  
163 234
/**
......
279 350
        aosDbgPrintf(">>> 3-4 (finish)\n");
280 351
        break;
281 352
      case STAGE_3_4_ABORT_ACTIVE:
282
        aosDbgPrintf(">>> 3-4 (avtive abort)\n");
353
        aosDbgPrintf(">>> 3-4 (active abort)\n");
283 354
        break;
284 355
      case STAGE_3_4_ABORT:
285 356
        aosDbgPrintf(">>> 3-4 (abort)\n");
......
314 385
      continue;
315 386
    }
316 387
    // if an IO event occurred
317
    if (eventmask & IOEVENT_MASK) {
388
    if (eventmask & _eventListenerIO.events) {
318 389
      ioflags = chEvtGetAndClearFlags(&_eventListenerIO);
319 390
      aosDbgPrintf("INFO: IO evt (0x%08X)\n", ioflags);
320 391
      // a power-down event occurred
......
345 416
      }
346 417
    }
347 418
    // an OS event occurred
348
    if (eventmask & OSEVENT_MASK) {
419
    if (eventmask & _eventListenerOS.events) {
349 420
      aosDbgPrintf("WARN: OS evt\n");
350 421
      // get the flags
351 422
      eventflags_t oseventflags = chEvtGetAndClearFlags(&_eventListenerOS);
......
357 428
#endif
358 429
    }
359 430
    // if a CAN event occurred
360
    if ((eventmask & CANEVENT_MASK)) {
431
    if ((eventmask & eventListenerCan.events)) {
361 432
      // fetch message
362 433
      if (flags.wfe) {
363 434
        canReceiveTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &canRxFrame, TIME_IMMEDIATE);
......
375 446
      // any further pending messages are fetched at the end of the loop
376 447
    }
377 448
    // if a timeout event occurred
378
    if (eventmask & TIMEOUTEVENT_MASK) {
449
    if (eventmask & eventListenerTimeout.events) {
379 450
      // is handled at the end of the loop (or must be cleared by FSM)
380 451
    }
381 452
    // if a delay event occurred
382
    if (eventmask & DELAYEVENT_MASK) {
453
    if (eventmask & eventListenerDelay.events) {
383 454
      // is handled by FSM
384 455
    }
385 456

  
......
423 494

  
424 495
#if (AMIROOS_CFG_SSSP_MASTER != true)
425 496
        // a CAN message was received
426
        else if (eventmask & CANEVENT_MASK) {
497
        else if (eventmask & eventListenerCan.events) {
427 498
          // if an initiation message was received
428 499
          if (canRxFrame.DLC == 0 &&
429 500
              canRxFrame.RTR == CAN_RTR_DATA &&
......
432 503
            aosDbgPrintf("init msg\n");
433 504
            // reset the timeout timer and clear pending flags
434 505
            chVTReset(&timerTimeout);
435
            chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
436
            eventmask &= ~TIMEOUTEVENT_MASK;
506
            chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
507
            eventmask &= ~(eventListenerTimeout.events);
437 508
            // activate S
438 509
            aosDbgPrintf("S+\n");
439 510
            apalControlGpioSet(&moduleSsspGpioSync, APAL_GPIO_ON);
......
467 538
          aosDbgPrintf("CAN -> ID (%u)\n", aos.sssp.moduleId);
468 539
          canTxFrame.DLC = 4;
469 540
          canTxFrame.SID = SSSP_STACKINIT_CANMSGID_MODULEID;
470
          _canSerialize32(canTxFrame.data8, aos.sssp.moduleId);
541
          _serialize(canTxFrame.data8, aos.sssp.moduleId, 4);
471 542
          if (canTransmitTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &canTxFrame, TIME_IMMEDIATE) != MSG_OK) {
472 543
            chEvtBroadcast(&eventSourceTimeout);
473 544
            break;
......
489 560
        }
490 561

  
491 562
        // if a delay event occurred
492
        if (eventmask & DELAYEVENT_MASK) {
563
        if (eventmask & eventListenerDelay.events) {
493 564
          // activate UP
494 565
          aosDbgPrintf("UP+\n");
495 566
          apalControlGpioSet(&moduleSsspGpioUp, APAL_GPIO_ON);
......
497 568
          aosDbgPrintf("S-\n");
498 569
          apalControlGpioSet(&moduleSsspGpioSync, APAL_GPIO_OFF);
499 570
          // explicitely clear timeout event flag
500
          chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
501
          eventmask &= ~TIMEOUTEVENT_MASK;
571
          chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
572
          eventmask &= ~(eventListenerTimeout.events);
502 573
          // proceed
503 574
          stage = STAGE_3_3_WAITFORID;
504 575
        }
......
513 584
        aos.sssp.stage = AOS_SSSP_STARTUP_3_3;
514 585

  
515 586
        // a CAN message was received
516
        if (eventmask & CANEVENT_MASK) {
587
        if (eventmask & eventListenerCan.events) {
517 588
          // if an ID message was received
518 589
          if (canRxFrame.DLC == 4 &&
519 590
              canRxFrame.RTR == CAN_RTR_DATA &&
520 591
              canRxFrame.IDE == CAN_IDE_STD &&
521 592
              canRxFrame.SID == SSSP_STACKINIT_CANMSGID_MODULEID) {
522
            aosDbgPrintf("ID (%u)\n", _canDeserialize32(canRxFrame.data8));
593
            aosDbgPrintf("ID (%u)\n", (uint32_t)_deserialize(canRxFrame.data8, 4));
523 594
            // validate received ID
524
            if (lastid < _canDeserialize32(canRxFrame.data8)) {
595
            if (lastid < _deserialize(canRxFrame.data8, 4)) {
525 596
              // store received ID
526
              lastid = _canDeserialize32(canRxFrame.data8);
597
              lastid = _deserialize(canRxFrame.data8, 4);
527 598
              // restart timeout timer
528 599
              chVTSet(&timerTimeout, LL_US2ST(AOS_SYSTEM_SSSP_TIMEOUT), _ssspTimerCallback, &eventSourceTimeout);
529 600
              // proceed
......
535 606
              flags.wfe_next = false;
536 607
            }
537 608
            // explicitely clear timeout event flag
538
            chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
539
            eventmask &= ~TIMEOUTEVENT_MASK;
609
            chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
610
            eventmask &= ~(eventListenerTimeout.events);
540 611
          }
541 612
        }
542 613
#endif
......
549 620
        aos.sssp.stage = AOS_SSSP_STARTUP_3_3;
550 621

  
551 622
        // a CAN message was received
552
        if (eventmask & CANEVENT_MASK) {
623
        if (eventmask & eventListenerCan.events) {
553 624
          // if an ID message was received
554 625
          if (canRxFrame.DLC == 4 &&
555 626
              canRxFrame.RTR == CAN_RTR_DATA &&
556 627
              canRxFrame.IDE == CAN_IDE_STD &&
557 628
              canRxFrame.SID == SSSP_STACKINIT_CANMSGID_MODULEID) {
558
            aosDbgPrintf("ID (%u)\n", _canDeserialize32(canRxFrame.data8));
629
            aosDbgPrintf("ID (%u)\n", (uint32_t)_deserialize(canRxFrame.data8, 4));
559 630
            // validate received ID
560
            if (lastid < _canDeserialize32(canRxFrame.data8)) {
631
            if (lastid < _deserialize(canRxFrame.data8, 4)) {
561 632
              // store received ID
562
              lastid = _canDeserialize32(canRxFrame.data8);
633
              lastid = _deserialize(canRxFrame.data8, 4);
563 634
              // restart timeout timer
564 635
              chVTSet(&timerTimeout, LL_US2ST(AOS_SYSTEM_SSSP_TIMEOUT), _ssspTimerCallback, &eventSourceTimeout);
565 636
            } else {
......
569 640
              flags.wfe_next = false;
570 641
            }
571 642
            // explicitely clear timeout event flag
572
            chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
573
            eventmask &= ~TIMEOUTEVENT_MASK;
643
            chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
644
            eventmask &= ~(eventListenerTimeout.events);
574 645
          }
575 646
        }
576 647

  
577 648
        // if an IO event was received (DN signal)
578
        if ((eventmask & IOEVENT_MASK) && (ioflags & MODULE_SSSP_EVENTFLAGS_DN)) {
649
        if ((eventmask & _eventListenerIO.events) && (ioflags & MODULE_SSSP_EVENTFLAGS_DN)) {
579 650
          aosDbgPrintf("DN <-\n");
580 651
          // reset timeout timer
581 652
          chVTReset(&timerTimeout);
582
          chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
583
          eventmask &= ~TIMEOUTEVENT_MASK;
653
          chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
654
          eventmask &= ~(eventListenerTimeout.events);
584 655
          // increment and broadcast ID
585 656
          aos.sssp.moduleId = lastid + 1;
586 657
          aosDbgPrintf("CAN -> ID (%u)\n", aos.sssp.moduleId);
587 658
          canTxFrame.DLC = 4;
588 659
          canTxFrame.SID = SSSP_STACKINIT_CANMSGID_MODULEID;
589
          _canSerialize32(canTxFrame.data8, aos.sssp.moduleId);
660
          _serialize(canTxFrame.data8, aos.sssp.moduleId, 4);
590 661
          if (canTransmitTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &canTxFrame, TIME_IMMEDIATE) != MSG_OK) {
591 662
            chEvtBroadcast(&eventSourceTimeout);
592 663
            break;
......
596 667
        }
597 668

  
598 669
        // if a delay event occurred
599
        if (eventmask & DELAYEVENT_MASK) {
670
        if (eventmask & eventListenerDelay.events) {
600 671
#if (AMIROOS_CFG_SSSP_STACK_END != true)
601 672
          // activate UP
602 673
          aosDbgPrintf("UP+\n");
......
607 678
          apalControlGpioSet(&moduleSsspGpioSync, APAL_GPIO_OFF);
608 679
          // reset the timeout timer
609 680
          chVTSet(&timerTimeout, LL_US2ST(AOS_SYSTEM_SSSP_TIMEOUT), _ssspTimerCallback, &eventSourceTimeout);
610
          chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
611
          eventmask &= ~TIMEOUTEVENT_MASK;
681
          chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
682
          eventmask &= ~(eventListenerTimeout.events);
612 683
          // proceed
613 684
          stage = STAGE_3_3_WAITFORID;
614 685
        }
......
623 694

  
624 695
#if (AMIROOS_CFG_SSSP_STACK_END != true)
625 696
        // a CAN message was received
626
        if (eventmask & CANEVENT_MASK) {
697
        if (eventmask & eventListenerCan.events) {
627 698
          // if an ID message was received
628 699
          if (canRxFrame.DLC == 4 &&
629 700
              canRxFrame.RTR == CAN_RTR_DATA &&
......
631 702
              canRxFrame.SID == SSSP_STACKINIT_CANMSGID_MODULEID) {
632 703
#if (AMIROOS_CFG_SSSP_STACK_START != true) || (AMIROOS_CFG_DBG == true)
633 704
            // Plausibility of the received ID is not checked at this point but is done by other modules still in a previous stage.
634
            lastid = _canDeserialize32(canRxFrame.data8);
705
            lastid = _deserialize(canRxFrame.data8, 4);
635 706
            aosDbgPrintf("ID (%u)\n", lastid);
636 707
#endif
637 708
            // restart timeout timer
638 709
            chVTSet(&timerTimeout, LL_US2ST(AOS_SYSTEM_SSSP_TIMEOUT), _ssspTimerCallback, &eventSourceTimeout);
639
            chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
640
            eventmask &= ~TIMEOUTEVENT_MASK;
710
            chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
711
            eventmask &= ~(eventListenerTimeout.events);
641 712
          }
642 713
        }
643 714
#endif
......
650 721
        aos.sssp.stage = AOS_SSSP_STARTUP_3_4;
651 722

  
652 723
        // if an IO event was received (S signal)
653
        if ((eventmask & IOEVENT_MASK) && (ioflags & MODULE_SSSP_EVENTFLAGS_SYNC)) {
724
        if ((eventmask & _eventListenerIO.events) && (ioflags & MODULE_SSSP_EVENTFLAGS_SYNC)) {
654 725
          // reset the timeout timer
655 726
          chVTReset(&timerTimeout);
656
          chEvtWaitAnyTimeout(TIMEOUTEVENT_MASK, TIME_IMMEDIATE);
657
          eventmask &= ~TIMEOUTEVENT_MASK;
727
          chEvtWaitAnyTimeout(eventListenerTimeout.events, TIME_IMMEDIATE);
728
          eventmask &= ~(eventListenerTimeout.events);
658 729
          //set the delay timer
659 730
          chVTSet(&timerDelay, LL_US2ST(AOS_SYSTEM_SSSP_TIMEOUT), _ssspTimerCallback, &eventSourceDelay);
660 731
        }
661 732

  
662 733
        // if a CAN event was received
663
        if (eventmask & CANEVENT_MASK) {
734
        if (eventmask & eventListenerCan.events) {
664 735
          // if an abort message was received
665 736
          if (canRxFrame.SID == SSSP_STACKINIT_CANMSGID_ABORT) {
666 737
            aosDbgPrintf("abort msg\n");
667 738
            // reset the delay timer
668 739
            chVTReset(&timerDelay);
669
            chEvtWaitAnyTimeout(DELAYEVENT_MASK, TIME_IMMEDIATE);
670
            eventmask &= ~DELAYEVENT_MASK;
740
            chEvtWaitAnyTimeout(eventListenerDelay.events, TIME_IMMEDIATE);
741
            eventmask &= ~(eventListenerDelay.events);
671 742
            // proceed
672 743
            stage = STAGE_3_4_ABORT;
673 744
          }
674 745
        }
675 746

  
676 747
        // if a delay timer event occurred
677
        if (eventmask & DELAYEVENT_MASK) {
748
        if (eventmask & eventListenerDelay.events) {
678 749
          aosDbgPrintf("sequence sucessful\n");
679 750
          // sequence finished sucessfully
680 751
          flags.loop = false;
......
693 764
        canTransmitTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &canTxFrame, TIME_INFINITE);
694 765
        aosDbgPrintf("CAN -> abort\n");
695 766
        // clear timeout flag
696
        eventmask &= ~TIMEOUTEVENT_MASK;
767
        eventmask &= ~(eventListenerTimeout.events);
697 768
        // proceed immediately
698 769
        stage = STAGE_3_4_ABORT;
699 770
        flags.wfe_next = false;
......
711 782
        aos.sssp.moduleId = 0;
712 783

  
713 784
        // if an IO event was received (S signal)
714
        if ((eventmask & IOEVENT_MASK) && (ioflags & MODULE_SSSP_EVENTFLAGS_SYNC)) {
785
        if ((eventmask & _eventListenerIO.events) && (ioflags & MODULE_SSSP_EVENTFLAGS_SYNC)) {
715 786
          aosDbgPrintf("sequence aborted\n");
716 787
          // exit the sequence
717 788
          flags.loop = false;
......
722 793
    }
723 794

  
724 795
    // fetch pending CAN message (if any)
725
    if ((eventmask & CANEVENT_MASK) && (canReceiveTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &canRxFrame, TIME_IMMEDIATE) == MSG_OK)) {
796
    if ((eventmask & eventListenerCan.events) && (canReceiveTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &canRxFrame, TIME_IMMEDIATE) == MSG_OK)) {
726 797
      aosDbgPrintf("CAN <- 0x%03X\n", canRxFrame.SID);
727 798
      flags.wfe_next = false;
728 799
    }
729 800

  
730 801
    // handle unhandled timeout events
731
    if (eventmask & TIMEOUTEVENT_MASK) {
802
    if (eventmask & eventListenerTimeout.events) {
732 803
      aosDbgPrintf("ERR: timeout evt\n");
733 804
      // abort
734 805
      flags.wfe_next = false;
......
831 902
#endif
832 903

  
833 904
#if (AMIROOS_CFG_TESTS_ENABLE == true)
905
#if defined(MODULE_INIT_TESTS)
834 906
  MODULE_INIT_TESTS();
907
#else
908
  #warning "MODULE_INIT_TESTS not defined"
909
#endif
835 910
#endif
836 911

  
837 912
#if defined(AMIROOS_CFG_MAIN_INIT_HOOK_4)
......
908 983
#endif
909 984

  
910 985
  /* SSSP startup OS synchronization phase (end of startup stage 2) */
911
  while ((eventmask = aosSysSsspStartupOsInitSyncCheck(&_eventListenerIO)) != 0) {
986
  while ((shutdown == AOS_SHUTDOWN_NONE) && (eventmask = aosSysSsspStartupOsInitSyncCheck(&_eventListenerIO)) != 0) {
912 987
    /*
913 988
     * This code is executed if the received event was not about the SYS_SYNC control signal.
914 989
     * The returned event could be caused by any listener (not only the argument).
915 990
     */
916
    // unexpected IO events
991
    // IO event
917 992
    if (eventmask & _eventListenerIO.events) {
918 993
      eventflags = chEvtGetAndClearFlags(&_eventListenerIO);
994
      // PD event
995
      if (eventflags & MODULE_SSSP_EVENTFLAGS_PD) {
996
        shutdown = AOS_SHUTDOWN_PASSIVE;
997
      } else {
919 998
#ifdef MODULE_SSSP_STARTUP_2_2_IOEVENT_HOOK
920
      MODULE_SSSP_STARTUP_2_2_IOEVENT_HOOK(eventmask, eventflags);
999
        MODULE_SSSP_STARTUP_2_2_IOEVENT_HOOK(eventmask, eventflags);
921 1000
#else
922
      _unexpectedEventError(eventmask, eventflags);
1001
        // ignore any other IO events
923 1002
#endif
1003
      }
924 1004
    }
925
    // unexpected OS event
1005
    // OS event
926 1006
    else if (eventmask & _eventListenerOS.events) {
927 1007
      eventflags = chEvtGetAndClearFlags(&_eventListenerOS);
928 1008
      _unexpectedEventError(eventmask, eventflags);
929 1009
    }
930
#if (AMIROOS_CFG_DBG == true)
931
    // unknown event (must never occur, thus disabled for release builds)
1010
    // unknown event
932 1011
    else {
933 1012
      _unexpectedEventError(eventmask, 0);
934 1013
    }
935
#endif
936 1014
  }
937 1015

  
938 1016
  /*
......
940 1018
   */
941 1019

  
942 1020
  /* SSSP startup stage 3 (module stack initialization) */
943
  shutdown = _ssspModuleStackInitialization();
1021
  if (shutdown == AOS_SHUTDOWN_NONE) {
1022
    shutdown = _ssspModuleStackInitialization();
1023
  }
1024

  
1025
  /*
1026
   * There must be no delays at this point, thus no hook is allowed.
1027
   */
1028

  
1029
  /* snychronize calendars */
1030
  if (shutdown == AOS_SHUTDOWN_NONE) {
1031
#if (AMIROOS_CFG_SSSP_MASTER == true)
1032
    CANTxFrame frame;
1033
    struct tm t;
1034
    uint64_t encoded;
1035

  
1036
    frame.DLC = 8;
1037
    frame.RTR = CAN_RTR_DATA;
1038
    frame.IDE = CAN_IDE_STD;
1039
    frame.SID = CALENDERSYNC_CANMSGID;
1040

  
1041
    aosDbgPrintf("transmitting current date/time...\t");
1042
    // get current date & time
1043
    aosSysGetDateTime(&t);
1044
    // encode
1045
    encoded = _TM2U64(&t);
1046
    // serialize
1047
    _serialize(frame.data8, encoded, 8);
1048
    // transmit
1049
    canTransmitTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &frame, TIME_IMMEDIATE);
1050

  
1051
    aosDbgPrintf("done\n");
1052
#else
1053
    CANRxFrame frame;
1054
    uint64_t encoded;
1055
    struct tm t;
1056

  
1057
    aosDbgPrintf("receiving current date/time...\t");
1058
    // receive message
1059
    if (canReceiveTimeout(&MODULE_HAL_CAN, CAN_ANY_MAILBOX, &frame, LL_US2ST(AOS_SYSTEM_SSSP_TIMEOUT)) == MSG_OK) {
1060
      // validate message
1061
      if (frame.DLC == 8 &&
1062
          frame.RTR == CAN_RTR_DATA &&
1063
          frame.IDE == CAN_IDE_STD &&
1064
          frame.SID == CALENDERSYNC_CANMSGID) {
1065
        // deserialize
1066
        encoded = _deserialize(frame.data8, 8);
1067
        // decode
1068
        _U642TM(&t, encoded);
1069
        // set current date & time
1070
        aosSysSetDateTime(&t);
1071
        aosDbgPrintf("success\n");
1072
      } else {
1073
        aosDbgPrintf("fail (invalid message)\n");
1074
      }
1075
    } else {
1076
      aosDbgPrintf("fail (timeout)\n");
1077
    }
1078
#endif
1079
    aosDbgPrintf("\n");
1080
  }
944 1081

  
945 1082
#if defined(AMIROOS_CFG_MAIN_INIT_HOOK_8)
946 1083
#if defined(AMIROOS_CFG_MAIN_INIT_HOOK_8_ARGS)
......
973 1110
  while (shutdown == AOS_SHUTDOWN_NONE) {
974 1111
    // wait for an event
975 1112
#if (AMIROOS_CFG_MAIN_LOOP_TIMEOUT != 0)
976
    eventmask = chEvtWaitOneTimeout(ALL_EVENTS, US2ST_LLD(AMIROOS_CFG_MAIN_LOOP_TIMEOUT));
1113
    eventmask = chEvtWaitOneTimeout(ALL_EVENTS, LL_US2ST(AMIROOS_CFG_MAIN_LOOP_TIMEOUT));
977 1114
#else
978 1115
    eventmask = chEvtWaitOne(ALL_EVENTS);
979 1116
#endif
os/core/src/aos_system.c
604 604
  aos_timestamp_t uptime;
605 605

  
606 606
  chSysLockFromISR();
607
  // get current uptime
608
  aosSysGetUptimeX(&uptime);
609
  // read signal S
610
  apalControlGpioGet(&moduleSsspGpioSync, &s_state);
611
  // if S was toggled from on to off during SSSP operation phase
612
  if (aos.sssp.stage == AOS_SSSP_OPERATION && s_state == APAL_GPIO_OFF) {
613
    // align the uptime with the synchronization period
614
    if (uptime % AMIROOS_CFG_SSSP_SYSSYNCPERIOD < AMIROOS_CFG_SSSP_SYSSYNCPERIOD / 2) {
615
      _uptime -= uptime % AMIROOS_CFG_SSSP_SYSSYNCPERIOD;
616
    } else {
617
      _uptime += AMIROOS_CFG_SSSP_SYSSYNCPERIOD - (uptime % AMIROOS_CFG_SSSP_SYSSYNCPERIOD);
607
  // if the system is in operation phase
608
  if (aos.sssp.stage == AOS_SSSP_OPERATION) {
609
    // read signal S
610
    apalControlGpioGet(&moduleSsspGpioSync, &s_state);
611
    // if S was toggled from on to off
612
    if (s_state == APAL_GPIO_OFF) {
613
      // get current uptime
614
      aosSysGetUptimeX(&uptime);
615
      // align the uptime with the synchronization period
616
      if (uptime % AMIROOS_CFG_SSSP_SYSSYNCPERIOD < AMIROOS_CFG_SSSP_SYSSYNCPERIOD / 2) {
617
        _uptime -= uptime % AMIROOS_CFG_SSSP_SYSSYNCPERIOD;
618
      } else {
619
        _uptime += AMIROOS_CFG_SSSP_SYSSYNCPERIOD - (uptime % AMIROOS_CFG_SSSP_SYSSYNCPERIOD);
620
      }
618 621
    }
619 622
  }
620 623
  // broadcast event
......
662 665
  aos_timestamp_t uptime;
663 666

  
664 667
  chSysLockFromISR();
665
  // read and toggle signal S
668
  // toggle and read signal S
669
  apalGpioToggle(moduleSsspGpioSync.gpio);
666 670
  apalControlGpioGet(&moduleSsspGpioSync, &s_state);
667
  s_state = (s_state == APAL_GPIO_ON) ? APAL_GPIO_OFF : APAL_GPIO_ON;
668
  apalControlGpioSet(&moduleSsspGpioSync, s_state);
669 671
  // if S was toggled from off to on
670 672
  if (s_state == APAL_GPIO_ON) {
671 673
    // reconfigure the timer precisely, because the logically falling edge (next interrupt) snychronizes the system time
......
749 751
  // update the system SSSP stage
750 752
  aos.sssp.stage = AOS_SSSP_OPERATION;
751 753

  
754
#if (AMIROOS_CFG_SSSP_MASTER == true)
755
  {
756
    chSysLock();
757
    // start the system synchronization counter
758
    // The first iteration of the timer is set to the next 'center' of a 'slice'.
759
    aos_timestamp_t t;
760
    aosSysGetUptimeX(&t);
761
    t = AMIROOS_CFG_SSSP_SYSSYNCPERIOD - (t % AMIROOS_CFG_SSSP_SYSSYNCPERIOD);
762
    chVTSetI(&_syssynctimer, LL_US2ST((t > (AMIROOS_CFG_SSSP_SYSSYNCPERIOD / 2)) ? (t - (AMIROOS_CFG_SSSP_SYSSYNCPERIOD / 2)) : (t + (AMIROOS_CFG_SSSP_SYSSYNCPERIOD / 2))), _sysSyncTimerCallback, NULL);
763
    chSysUnlock();
764
  }
765
#endif
766

  
752 767
  // print system information;
753 768
  _printSystemInfo((BaseSequentialStream*)&aos.iostream);
754 769
  aosprintf("\n");
......
796 811
      f == MODULE_SSSP_EVENTFLAGS_SYNC &&
797 812
      s == APAL_GPIO_OFF) {
798 813
    chSysLock();
799
#if (AMIROOS_CFG_SSSP_MASTER == true)
800
    // start the systen synchronization counter
801
    chVTSetI(&_syssynctimer, LL_US2ST(AMIROOS_CFG_SSSP_SYSSYNCPERIOD / 2), &_sysSyncTimerCallback, NULL);
802
#endif
803 814
    // start the uptime counter
804 815
    _synctime = chVTGetSystemTimeX();
805 816
    _uptime = 0;

Also available in: Unified diff