Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Firmware/LoRaSerial/LoRaSerial.ino
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ const int FIRMWARE_VERSION_MINOR = 0;
#define UNIQUE_ID_BYTES 16 //Number of bytes in the unique ID

//Frame lengths
#define MP_HEARTBEAT_BYTES 1 //Number of data bytes in the MP_HEARTBEAT frame
#define MP_HEARTBEAT_BYTES (sizeof(uint8_t) + sizeof(unsigned long)) //Number of data bytes in the MP_HEARTBEAT frame
#define P2P_FIND_PARTNER_BYTES sizeof(unsigned long) //Number of data bytes in the FIND_PARTNER frame
#define P2P_SYNC_CLOCKS_BYTES (sizeof(uint8_t) + sizeof(unsigned long)) //Number of data bytes in the SYNC_CLOCKS frame
#define P2P_ZERO_ACKS_BYTES sizeof(unsigned long) //Number of data bytes in the ZERO_ACKS frame
Expand Down
72 changes: 57 additions & 15 deletions Firmware/LoRaSerial/Radio.ino
Original file line number Diff line number Diff line change
Expand Up @@ -931,8 +931,7 @@ bool xmitDatagramP2PSyncClocks()
radioCallHistory[RADIO_CALL_xmitDatagramP2PSyncClocks] = currentMillis;

startOfData = endOfTxData;
memcpy(endOfTxData, &channelNumber, sizeof(channelNumber));
endOfTxData += sizeof(channelNumber);
*endOfTxData++ = channelNumber;

memcpy(endOfTxData, &currentMillis, sizeof(currentMillis));
endOfTxData += sizeof(unsigned long);
Expand Down Expand Up @@ -1149,18 +1148,20 @@ bool xmitDatagramMpHeartbeat()
radioCallHistory[RADIO_CALL_xmitDatagramMpHeartbeat] = millis();

startOfData = endOfTxData;
memcpy(endOfTxData, &channelNumber, sizeof(channelNumber));
endOfTxData += sizeof(channelNumber);
*endOfTxData++ = channelNumber;

memcpy(endOfTxData, &currentMillis, sizeof(currentMillis));
endOfTxData += sizeof(unsigned long);

/*
endOfTxData ---.
|
V
+----------+---------+----------+------------+---------+----------+
| Optional | | Optional | Optional | Channel | |
| NET ID | Control | C-Timer | SF6 Length | Number | Trailer |
| 8 bits | 8 bits | 2 bytes | 8 bits | 1 byte | n Bytes |
+----------+---------+----------+------------+---------+----------+
endOfTxData ---.
|
V
+----------+---------+----------+------------+---------+---------+----------+
| Optional | | Optional | Optional | Channel | | |
| NET ID | Control | C-Timer | SF6 Length | Number | Millis | Trailer |
| 8 bits | 8 bits | 2 bytes | 8 bits | 1 byte | 4 bytes | n Bytes |
+----------+---------+----------+------------+---------+---------+----------+
*/

//Verify the data length
Expand Down Expand Up @@ -3249,7 +3250,7 @@ void stopChannelTimer()

//Given the remote unit's number of ms before its next hop,
//adjust our own channelTimer interrupt to be synchronized with the remote unit
void syncChannelTimer(uint32_t frameAirTimeUsec)
void syncChannelTimer(uint32_t frameAirTimeUsec, bool clockStarting)
{
int16_t adjustment;
uint8_t caseNumber;
Expand Down Expand Up @@ -3317,6 +3318,48 @@ void syncChannelTimer(uint32_t frameAirTimeUsec)
//timer update will add only microseconds to when the hop is done.
delayedHopCount = timeToHop ? 1 : 0;

// 4800 BPS operation
//
// |<---------------- Millis to HOP ---------------->|
// _____ | |_____________
// |_|_________________________________________________|
// | | |
// TX Start ^ TX Complete ^ |<-- rmtHopTimeMsec -->|
// RX Complete ^
//
//
// 150 BPS operation
//
// |<--- Millis to HOP --->|
// _____ | |_________________________
// |_|_______________________| | |_____________
// | | |
// TX Start ^ TX Complete ^ | |
// RX Complete ^ |
// |<- ->|
// rmtHopTimeMsec
//
// Millis to HOP
// |<- ->|
// | |_________________________ __
// ___________|_____| |_________________________|
// | | |
// TX Start ^ TX Complete ^ | |
// RX Complete ^ |
// |<---- ---->|
// rmtHopTimeMsec
//
//For low speed operation move the TX start into the current dwell time period
//to make the rest of the math look like the 4800 BPS operation.
frameAirTimeMsec = settings.maxDwellTime - msToNextHopRemote
+ (frameAirTimeUsec + settings.txToRxUsec + micros() - transactionCompleteMicros) / 1000;
while (frameAirTimeMsec >= (settings.maxDwellTime + (settings.maxDwellTime >> 6)))
{
frameAirTimeMsec -= settings.maxDwellTime;
if (clockStarting)
delayedHopCount += 1; //Account for the missing hop when the timer is stopped
}

//The radios are using the same frequencies since the frame was successfully
//received. The goal is to adjust the channel timer to fire in close proximity
//to the firing of the remote sysstem's channel timer. The following cases
Expand All @@ -3337,8 +3380,7 @@ void syncChannelTimer(uint32_t frameAirTimeUsec)
//Compute the remote system's channel timer firing time offset in milliseconds
//using the channel timer value and the adjustments for transmit and receive
//time (time of flight)
frameAirTimeMsec = (frameAirTimeUsec + settings.txToRxUsec + micros() - transactionCompleteMicros) / 1000;
rmtHopTimeMsec = msToNextHopRemote - frameAirTimeMsec;
rmtHopTimeMsec = settings.maxDwellTime - frameAirTimeMsec;

//Compute when the local system last hopped
lclHopTimeMsec = currentMillis - channelTimerStart;
Expand Down
13 changes: 6 additions & 7 deletions Firmware/LoRaSerial/States.ino
Original file line number Diff line number Diff line change
Expand Up @@ -750,7 +750,7 @@ void updateRadioState()
COMPUTE_TIMESTAMP_OFFSET(rxData, 1, txDataAckUsec);

//The datagram we are expecting
syncChannelTimer(txDataAckUsec); //Adjust freq hop ISR based on remote's remaining clock
syncChannelTimer(txDataAckUsec, 0); //Adjust freq hop ISR based on remote's remaining clock

triggerEvent(TRIGGER_RX_ACK);

Expand Down Expand Up @@ -1067,9 +1067,9 @@ void updateRadioState()
//then skip active discovery and go to standby
if (((frameAirTimeUsec + txDataAckUsec + settings.txToRxUsec) / 1000) > (settings.maxDwellTime / 2))
{
stopChannelTimer();
channelNumber = 0;
setRadioFrequency(false);
stopChannelTimer();
changeState(RADIO_DISCOVER_STANDBY);
}
else
Expand Down Expand Up @@ -1160,7 +1160,7 @@ void updateRadioState()
//Start and adjust freq hop ISR based on remote's remaining clock
startChannelTimer();
channelTimerStart -= settings.maxDwellTime;
syncChannelTimer(txSyncClocksUsec);
syncChannelTimer(txSyncClocksUsec, 1);
triggerEvent(TRIGGER_RX_SYNC_CLOCKS);

if (settings.debugSync)
Expand Down Expand Up @@ -1304,8 +1304,7 @@ void updateRadioState()
//Start and adjust freq hop ISR based on remote's remaining clock
startChannelTimer();
channelTimerStart -= settings.maxDwellTime;
syncChannelTimer(txSyncClocksUsec);
triggerEvent(TRIGGER_RX_SYNC_CLOCKS);
syncChannelTimer(txSyncClocksUsec, 1);

if (settings.debugSync)
{
Expand Down Expand Up @@ -1423,7 +1422,7 @@ void updateRadioState()
if (settings.server == false)
{
//Adjust freq hop ISR based on server's remaining clock
syncChannelTimer(txHeartbeatUsec);
syncChannelTimer(txHeartbeatUsec, 0);

//Received heartbeat - do not ack.
triggerEvent(TRIGGER_RX_HEARTBEAT);
Expand Down Expand Up @@ -3225,7 +3224,7 @@ void vcReceiveHeartbeat(uint32_t rxMillis)

//Adjust freq hop ISR based on server's remaining clock
if ((rxSrcVc == VC_SERVER) || (memcmp(rxVcData, myUniqueId, sizeof(myUniqueId)) == 0))
syncChannelTimer(txHeartbeatUsec);
syncChannelTimer(txHeartbeatUsec, 0);

//Update the timestamp offset
if (rxSrcVc == VC_SERVER)
Expand Down