4 #include "serial_irq.h"
5 #include "serial_dma.h"
10 #include "main_comm.h"
14 * Devices 1 and 2 synchronize clocks using serial messages.
16 * 1. Each serial message timestamped using the hardware timer capture
17 * registers in both the sender and receiver.
18 * 2. The sender transmits the send timestamp during the next time-sync
20 * 3. The receiver then compares the senders timestamp with it's own
21 * timestamp for the corresponding messages and calculates an offset.
22 * 4. The offset is used to compensate the receivers local clock.
24 * Time synchronization is performed in both directions.
32 #define N_ELEM(x) (sizeof(x) / sizeof((x)[0]))
36 void (*task)(uint64_t, uint64_t);
42 void task_serial(uint64_t local, uint64_t world);
43 void task_events(uint64_t local, uint64_t world);
44 void task_sync(uint64_t local, uint64_t world);
45 void task_leds(uint64_t local, uint64_t world);
46 void task_emit(uint64_t local, uint64_t world);
47 void task_debug(uint64_t local, uint64_t world);
51 { task_serial, 0 }, // always
52 { task_events, 0 }, // always -- testing
53 { task_sync, 0 }, // always
54 { task_emit, 0 }, // always
55 { task_leds, 100000000 }, // 10hz
56 { task_debug, 1000000000 }, // 1hz
64 DigitalOut led1(LED1);
65 DigitalOut led2(LED2);
86 void task_serial(uint64_t local, uint64_t world)
88 while (sirq_ready(sirq_dbg)) {
89 //sirq_printf("serial recv - dbg\r\n");
90 msg_receive(&parser_dbg, sirq_getc(sirq_dbg));
93 while (sirq_ready(sirq_bbb)) {
94 //sirq_printf("serial recv - bbb\r\n");
95 msg_receive(&parser_bbb, sirq_getc(sirq_bbb));
98 while (sirq_ready(sirq_mbed)) {
99 //sirq_printf("serial recv - mbed\r\n");
100 msg_receive(&parser_mbed, sirq_getc(sirq_mbed));
104 void task_events(uint64_t local, uint64_t world)
109 if (tdma_stamp(tdma_evt, &event)) {
110 sirq_printf("event received - evt\r\n");
111 if (tdma_stamp(tdma_rcv, &event))
112 sirq_printf("event received - rcv\r\n");
113 if (tdma_stamp(tdma_xmt, &event))
114 sirq_printf("event received - xmt\r\n");
117 if (tdma_stamp(tdma_evt, &event))
118 comm_send_event(0, event);
119 tdma_stop(tdma_evt, 0);
120 tdma_start(tdma_evt);
123 void task_sync(uint64_t local, uint64_t world)
125 comm_send_sync(local);
128 void task_leds(uint64_t local, uint64_t world)
130 static uint32_t which = 0;
136 void task_emit(uint64_t local, uint64_t world)
138 emit_transmit(local, world);
141 void task_debug(uint64_t local, uint64_t world)
143 //tdma_debug(tdma_rcv);
144 //tdma_debug(tdma_xmt);
146 //sirq_debug(sirq_mbed);
148 comm_send_event(1, local);
151 sirq_printf("background - %6u.%02u -> %u.%02u\r\n",
152 (uint32_t)(local / NSEC_PER_SEC),
153 (uint32_t)(local % NSEC_PER_SEC / 10000000),
154 (uint32_t)(world / NSEC_PER_SEC),
155 (uint32_t)(world % NSEC_PER_SEC / 10000000));
163 void background(void)
166 uint64_t local = tdma_time();
167 uint64_t world = time_to_world(local);
170 for (unsigned i = 0; i < N_ELEM(tasks); i++) {
171 if (local >= tasks[i].due) {
172 tasks[i].task(local, world);
173 tasks[i].due += tasks[i].period;
178 int main(int argc, char **argv)
181 sirq_dbg = sirq_open(SIRQ_UART0, USBTX, USBRX, 115200, 0); // to pc
182 sirq_bbb = sirq_open(SIRQ_UART1, PTE0, PTE1, 115200, 0); // to bbb
183 sirq_mbed = sirq_open(SIRQ_UART2, PTD3, PTD2, 115200, 1); // to mbed
186 tdma_evt = tdma_open(TDMA_CHAN0, 3, PTC9, PullDown); // async event
187 tdma_rcv = tdma_open(TDMA_CHAN2, 3, PTD2, PullUp); // time sync rcv
188 tdma_xmt = tdma_open(TDMA_CHAN3, 3, PTD3, PullUp); // time sync xmt
190 // Setup event generation
192 emit_init(3, PTE20, PullDown);
193 comm_init(sirq_dbg, sirq_bbb, sirq_mbed,
197 msg_register(&parser_dbg, MSG_ID_INIT, (handler_t)comm_handle_init);
198 msg_register(&parser_dbg, MSG_ID_SYNC, (handler_t)comm_handle_sync);
199 msg_register(&parser_dbg, MSG_ID_EVENT, (handler_t)comm_handle_event);
201 msg_register(&parser_bbb, MSG_ID_INIT, (handler_t)comm_handle_init);
203 msg_register(&parser_mbed, MSG_ID_SYNC, (handler_t)comm_handle_sync);
204 msg_register(&parser_mbed, MSG_ID_EVENT, (handler_t)comm_handle_event);
207 tdma_start(tdma_evt);
208 tdma_start(tdma_rcv);
209 tdma_start(tdma_xmt);
211 // Run background loop