]> git.tdb.fi Git - model-railway-devices.git/commitdiff
Support chaining packets to create a larger packet
authorMikko Rasa <tdb@tdb.fi>
Sun, 3 Nov 2013 09:20:42 +0000 (11:20 +0200)
committerMikko Rasa <tdb@tdb.fi>
Sun, 3 Nov 2013 09:20:42 +0000 (11:20 +0200)
MFX packets with response windows won't fit into the 256 bits available
in a single packet structure.  I'd rather keep the length field 8-bit to
preserve atomicity, and this also allows certain tricks later that would
be harder to do with a single packet.

arducontrol/output.c
arducontrol/output.h

index 673f23242d0b93aab450ea1eb4129ad3acb531a7..e017560c5cf6e12930f3b65003b4eae1823868b0 100644 (file)
@@ -14,7 +14,9 @@ enum State
        SENDING
 };
 
-OutputPacket packet;
+OutputPacket packets[4];
+uint8_t chain_length;
+uint8_t current_packet;
 volatile uint8_t packet_state = IDLE;
 static uint8_t out_bit;
 static uint8_t out_time;
@@ -32,7 +34,14 @@ void output_init(void)
 OutputPacket *output_create_packet(void)
 {
        while(packet_state!=IDLE) ;
-       return &packet;
+       chain_length = 1;
+       return &packets[0];
+}
+
+OutputPacket *output_create_chained_packet(void)
+{
+       ++chain_length;
+       return &packets[chain_length-1];
 }
 
 void output_send_packet(void)
@@ -40,6 +49,7 @@ void output_send_packet(void)
        if(packet_state!=IDLE)
                return;
 
+       current_packet = 0;
        packet_state = READY;
 }
 
@@ -88,27 +98,29 @@ static inline void output_tick(void)
 
        if(out_time && !--out_time)
        {
+               OutputPacket *packet = &packets[current_packet];
                ++out_bit;
-               if(out_bit>=packet.length)
+               if(out_bit>=packet->length)
                {
                        PORTD &= ~BIT(POLARITY);
-                       if(packet.repeat_count>1)
+                       if(--packet->repeat_count)
                        {
-                               if(packet.repeat_count<0xFF)
-                                       --packet.repeat_count;
-                               delay_time = packet.repeat_delay;
+                               delay_time = packet->repeat_delay;
                                packet_state = READY;
                        }
                        else
                        {
-                               delay_time = packet.final_delay;
-                               packet_state = IDLE;
+                               delay_time = packet->final_delay;
+                               if(++current_packet<chain_length)
+                                       packet_state = READY;
+                               else
+                                       packet_state = IDLE;
                        }
                }
                else
                {
                        if((out_bit&7)==0)
-                               out_data = packet.data[out_bit>>3];
+                               out_data = packet->data[out_bit>>3];
                        else
                                out_data >>= 1;
 
@@ -117,7 +129,7 @@ static inline void output_tick(void)
                        else
                                PORTD &= ~BIT(POLARITY);
 
-                       out_time = packet.bit_duration;
+                       out_time = packet->bit_duration;
                }
 
                return;
@@ -125,10 +137,11 @@ static inline void output_tick(void)
 
        if(packet_state==READY)
        {
+               OutputPacket *packet = &packets[current_packet];
                packet_state = SENDING;
                out_bit = 0;
-               out_time = packet.bit_duration;
-               out_data = packet.data[0];
+               out_time = packet->bit_duration;
+               out_data = packet->data[0];
                if(out_data&1)
                        PORTD |= BIT(POLARITY);
                else
index 162e1e010b4a168f87773583bcd2c3aa1a10946a..2fde2627f3f05d2818b6a581eb0883309dbd2b97 100644 (file)
@@ -15,6 +15,7 @@ typedef struct
 
 void output_init(void);
 OutputPacket *output_create_packet(void);
+OutputPacket *output_create_chained_packet(void);
 void output_send_packet(void);
 void output_set_power(uint8_t);
 uint8_t output_is_power_on();