Added airtime limiting and channel timing stat reporting over serial/USB/bluetooth
This commit is contained in:
		
							
								
								
									
										3
									
								
								Config.h
									
									
									
									
									
								
							
							
						
						
									
										3
									
								
								Config.h
									
									
									
									
									
								
							@@ -359,6 +359,9 @@
 | 
			
		||||
		float us_per_byte = 0.0;
 | 
			
		||||
		#define current_airtime_bin(void) (millis()%AIRTIME_LONGTERM_MS)/AIRTIME_BINLEN_MS
 | 
			
		||||
	#endif
 | 
			
		||||
	float st_airtime_limit = 0.0;
 | 
			
		||||
	float lt_airtime_limit = 0.0;
 | 
			
		||||
	bool airtime_lock = false;
 | 
			
		||||
 | 
			
		||||
	bool stat_signal_detected = false;
 | 
			
		||||
	bool stat_signal_synced   = false;
 | 
			
		||||
 
 | 
			
		||||
@@ -33,6 +33,8 @@
 | 
			
		||||
  #define CMD_DETECT      0x08
 | 
			
		||||
  #define CMD_IMPLICIT    0x09
 | 
			
		||||
  #define CMD_LEAVE       0x0A
 | 
			
		||||
  #define CMD_ST_ALOCK    0x0B
 | 
			
		||||
  #define CMD_LT_ALOCK    0x0C
 | 
			
		||||
  #define CMD_PROMISC     0x0E
 | 
			
		||||
  #define CMD_READY       0x0F
 | 
			
		||||
 | 
			
		||||
@@ -40,6 +42,7 @@
 | 
			
		||||
  #define CMD_STAT_TX     0x22
 | 
			
		||||
  #define CMD_STAT_RSSI   0x23
 | 
			
		||||
  #define CMD_STAT_SNR    0x24
 | 
			
		||||
  #define CMD_STAT_CHTM   0x25
 | 
			
		||||
  #define CMD_BLINK       0x30
 | 
			
		||||
  #define CMD_RANDOM      0x40
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -312,6 +312,8 @@ bool startRadio() {
 | 
			
		||||
      } else {
 | 
			
		||||
        radio_online = true;
 | 
			
		||||
 | 
			
		||||
        init_channel_stats();
 | 
			
		||||
 | 
			
		||||
        setTXPower();
 | 
			
		||||
        setBandwidth();
 | 
			
		||||
        setSpreadingFactor();
 | 
			
		||||
@@ -395,6 +397,9 @@ void flushQueue(void) {
 | 
			
		||||
 | 
			
		||||
  queue_height = 0;
 | 
			
		||||
  queued_bytes = 0;
 | 
			
		||||
  #if MCU_VARIANT == MCU_ESP32
 | 
			
		||||
    update_airtime();
 | 
			
		||||
  #endif
 | 
			
		||||
  queue_flushing = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -427,6 +432,8 @@ void update_airtime() {
 | 
			
		||||
      longterm_channel_util_sum += longterm_bins[bin];
 | 
			
		||||
    }
 | 
			
		||||
    longterm_channel_util = (float)longterm_channel_util_sum/(float)AIRTIME_BINS;
 | 
			
		||||
 | 
			
		||||
    kiss_indicate_channel_stats();
 | 
			
		||||
  #endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -650,6 +657,52 @@ void serialCallback(uint8_t sbyte) {
 | 
			
		||||
        startRadio();
 | 
			
		||||
        kiss_indicate_radiostate();
 | 
			
		||||
      }
 | 
			
		||||
    } else if (command == CMD_ST_ALOCK) {
 | 
			
		||||
      if (sbyte == FESC) {
 | 
			
		||||
            ESCAPE = true;
 | 
			
		||||
        } else {
 | 
			
		||||
            if (ESCAPE) {
 | 
			
		||||
                if (sbyte == TFEND) sbyte = FEND;
 | 
			
		||||
                if (sbyte == TFESC) sbyte = FESC;
 | 
			
		||||
                ESCAPE = false;
 | 
			
		||||
            }
 | 
			
		||||
            if (frame_len < CMD_L) cmdbuf[frame_len++] = sbyte;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (frame_len == 2) {
 | 
			
		||||
          uint16_t at = (uint16_t)cmdbuf[0] << 8 | (uint16_t)cmdbuf[1];
 | 
			
		||||
 | 
			
		||||
          if (at == 0) {
 | 
			
		||||
            st_airtime_limit = 0.0;
 | 
			
		||||
          } else {
 | 
			
		||||
            st_airtime_limit = (float)at/(100.0*100.0);
 | 
			
		||||
            if (st_airtime_limit >= 1.0) { st_airtime_limit = 0.0; }
 | 
			
		||||
          }
 | 
			
		||||
          kiss_indicate_st_alock();
 | 
			
		||||
        }
 | 
			
		||||
    } else if (command == CMD_LT_ALOCK) {
 | 
			
		||||
      if (sbyte == FESC) {
 | 
			
		||||
            ESCAPE = true;
 | 
			
		||||
        } else {
 | 
			
		||||
            if (ESCAPE) {
 | 
			
		||||
                if (sbyte == TFEND) sbyte = FEND;
 | 
			
		||||
                if (sbyte == TFESC) sbyte = FESC;
 | 
			
		||||
                ESCAPE = false;
 | 
			
		||||
            }
 | 
			
		||||
            if (frame_len < CMD_L) cmdbuf[frame_len++] = sbyte;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (frame_len == 2) {
 | 
			
		||||
          uint16_t at = (uint16_t)cmdbuf[0] << 8 | (uint16_t)cmdbuf[1];
 | 
			
		||||
 | 
			
		||||
          if (at == 0) {
 | 
			
		||||
            lt_airtime_limit = 0.0;
 | 
			
		||||
          } else {
 | 
			
		||||
            lt_airtime_limit = (float)at/(100.0*100.0);
 | 
			
		||||
            if (lt_airtime_limit >= 1.0) { lt_airtime_limit = 0.0; }
 | 
			
		||||
          }
 | 
			
		||||
          kiss_indicate_lt_alock();
 | 
			
		||||
        }
 | 
			
		||||
    } else if (command == CMD_STAT_RX) {
 | 
			
		||||
      kiss_indicate_stat_rx();
 | 
			
		||||
    } else if (command == CMD_STAT_TX) {
 | 
			
		||||
@@ -885,7 +938,11 @@ void updateModemStatus() {
 | 
			
		||||
  if (dcd_led) {
 | 
			
		||||
    led_rx_on();
 | 
			
		||||
  } else {
 | 
			
		||||
    led_rx_off();
 | 
			
		||||
    if (airtime_lock) {
 | 
			
		||||
      led_indicate_airtime_lock();
 | 
			
		||||
    } else {
 | 
			
		||||
      led_rx_off();
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -905,7 +962,10 @@ void checkModemStatus() {
 | 
			
		||||
        total_channel_util = local_channel_util + airtime;
 | 
			
		||||
        if (total_channel_util > 1.0) total_channel_util = 1.0;
 | 
			
		||||
 | 
			
		||||
        longterm_bins[current_airtime_bin()] = total_channel_util;
 | 
			
		||||
        int16_t cb = current_airtime_bin();
 | 
			
		||||
        uint16_t nb = cb+1; if (nb == AIRTIME_BINS) { nb = 0; }
 | 
			
		||||
        if (total_channel_util > longterm_bins[cb]) longterm_bins[cb] = total_channel_util;
 | 
			
		||||
        longterm_bins[nb] = 0.0;
 | 
			
		||||
 | 
			
		||||
        update_airtime();
 | 
			
		||||
      }
 | 
			
		||||
@@ -1047,23 +1107,29 @@ void loop() {
 | 
			
		||||
        kiss_indicate_stat_snr();
 | 
			
		||||
        kiss_write_packet();
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      airtime_lock = false;
 | 
			
		||||
      if (st_airtime_limit != 0.0 && airtime >= st_airtime_limit) airtime_lock = true;
 | 
			
		||||
      if (lt_airtime_limit != 0.0 && longterm_airtime >= lt_airtime_limit) airtime_lock = true;
 | 
			
		||||
    #endif
 | 
			
		||||
 | 
			
		||||
    if (queue_height > 0) {
 | 
			
		||||
      if (!dcd_waiting) updateModemStatus();
 | 
			
		||||
    if (!airtime_lock) {
 | 
			
		||||
      if (queue_height > 0) {
 | 
			
		||||
        if (!dcd_waiting) updateModemStatus();
 | 
			
		||||
 | 
			
		||||
      if (!dcd && !dcd_led) {
 | 
			
		||||
        if (dcd_waiting) delay(lora_rx_turnaround_ms);
 | 
			
		||||
        if (!dcd && !dcd_led) {
 | 
			
		||||
          if (dcd_waiting) delay(lora_rx_turnaround_ms);
 | 
			
		||||
 | 
			
		||||
        updateModemStatus();
 | 
			
		||||
          updateModemStatus();
 | 
			
		||||
 | 
			
		||||
        if (!dcd) {
 | 
			
		||||
          dcd_waiting = false;
 | 
			
		||||
          flushQueue();
 | 
			
		||||
          if (!dcd) {
 | 
			
		||||
            dcd_waiting = false;
 | 
			
		||||
            flushQueue();
 | 
			
		||||
          }
 | 
			
		||||
 | 
			
		||||
        } else {
 | 
			
		||||
          dcd_waiting = true;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
      } else {
 | 
			
		||||
        dcd_waiting = true;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  
 | 
			
		||||
 
 | 
			
		||||
										
											Binary file not shown.
										
									
								
							
							
								
								
									
										61
									
								
								Utilities.h
									
									
									
									
									
								
							
							
						
						
									
										61
									
								
								Utilities.h
									
									
									
									
									
								
							@@ -218,6 +218,13 @@ void led_indicate_error(int cycles) {
 | 
			
		||||
	#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// LED Indication: Airtime Lock
 | 
			
		||||
void led_indicate_airtime_lock() {
 | 
			
		||||
	#if HAS_NP == true
 | 
			
		||||
		npset(32,0,2);
 | 
			
		||||
	#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// LED Indication: Boot Error
 | 
			
		||||
void led_indicate_boot_error() {
 | 
			
		||||
	#if HAS_NP == true
 | 
			
		||||
@@ -687,6 +694,44 @@ void kiss_indicate_frequency() {
 | 
			
		||||
	serial_write(FEND);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void kiss_indicate_st_alock() {
 | 
			
		||||
	uint16_t at = (uint16_t)(st_airtime_limit*100*100);
 | 
			
		||||
	serial_write(FEND);
 | 
			
		||||
	serial_write(CMD_ST_ALOCK);
 | 
			
		||||
	escaped_serial_write(at>>8);
 | 
			
		||||
	escaped_serial_write(at);
 | 
			
		||||
	serial_write(FEND);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void kiss_indicate_lt_alock() {
 | 
			
		||||
	uint16_t at = (uint16_t)(lt_airtime_limit*100*100);
 | 
			
		||||
	serial_write(FEND);
 | 
			
		||||
	serial_write(CMD_LT_ALOCK);
 | 
			
		||||
	escaped_serial_write(at>>8);
 | 
			
		||||
	escaped_serial_write(at);
 | 
			
		||||
	serial_write(FEND);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void kiss_indicate_channel_stats() {
 | 
			
		||||
	#if MCU_VARIANT == MCU_ESP32
 | 
			
		||||
		uint16_t ats = (uint16_t)(airtime*100*100);
 | 
			
		||||
		uint16_t atl = (uint16_t)(longterm_airtime*100*100);
 | 
			
		||||
		uint16_t cls = (uint16_t)(total_channel_util*100*100);
 | 
			
		||||
		uint16_t cll = (uint16_t)(longterm_channel_util*100*100);
 | 
			
		||||
		serial_write(FEND);
 | 
			
		||||
		serial_write(CMD_STAT_CHTM);
 | 
			
		||||
		escaped_serial_write(ats>>8);
 | 
			
		||||
		escaped_serial_write(ats);
 | 
			
		||||
		escaped_serial_write(atl>>8);
 | 
			
		||||
		escaped_serial_write(atl);
 | 
			
		||||
		escaped_serial_write(cls>>8);
 | 
			
		||||
		escaped_serial_write(cls);
 | 
			
		||||
		escaped_serial_write(cll>>8);
 | 
			
		||||
		escaped_serial_write(cll);
 | 
			
		||||
		serial_write(FEND);
 | 
			
		||||
	#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void kiss_indicate_btpin() {
 | 
			
		||||
	#if HAS_BLUETOOTH
 | 
			
		||||
		serial_write(FEND);
 | 
			
		||||
@@ -1182,13 +1227,15 @@ void unlock_rom() {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void init_channel_stats() {
 | 
			
		||||
	for (uint16_t ai = 0; ai < DCD_SAMPLES; ai++) { util_samples[ai] = false; }
 | 
			
		||||
	for (uint16_t ai = 0; ai < AIRTIME_BINS; ai++) { airtime_bins[ai] = 0; }
 | 
			
		||||
	for (uint16_t ai = 0; ai < AIRTIME_BINS; ai++) { longterm_bins[ai] = 0.0; }
 | 
			
		||||
	local_channel_util = 0.0;
 | 
			
		||||
	total_channel_util = 0.0;
 | 
			
		||||
	airtime = 0.0;
 | 
			
		||||
	longterm_airtime = 0.0;
 | 
			
		||||
	#if MCU_VARIANT == MCU_ESP32
 | 
			
		||||
		for (uint16_t ai = 0; ai < DCD_SAMPLES; ai++) { util_samples[ai] = false; }
 | 
			
		||||
		for (uint16_t ai = 0; ai < AIRTIME_BINS; ai++) { airtime_bins[ai] = 0; }
 | 
			
		||||
		for (uint16_t ai = 0; ai < AIRTIME_BINS; ai++) { longterm_bins[ai] = 0.0; }
 | 
			
		||||
		local_channel_util = 0.0;
 | 
			
		||||
		total_channel_util = 0.0;
 | 
			
		||||
		airtime = 0.0;
 | 
			
		||||
		longterm_airtime = 0.0;
 | 
			
		||||
	#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
typedef struct FIFOBuffer
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user