moved from upshift downshift to speed level int

This commit is contained in:
DJ2LS 2024-02-22 21:15:43 +01:00
parent 0100104afb
commit 3574f76a79
4 changed files with 57 additions and 64 deletions

View file

@ -44,6 +44,8 @@ class ARQSession():
self.modem = modem self.modem = modem
self.speed_level = 0 self.speed_level = 0
self.previous_speed_level = 0
self.frames_per_burst = 1 self.frames_per_burst = 1
self.frame_factory = data_frame_factory.DataFrameFactory(self.config) self.frame_factory = data_frame_factory.DataFrameFactory(self.config)
@ -97,7 +99,6 @@ class ARQSession():
received_data, type_byte = getattr(self, action_name)(frame) received_data, type_byte = getattr(self, action_name)(frame)
if isinstance(received_data, bytearray) and isinstance(type_byte, int): if isinstance(received_data, bytearray) and isinstance(type_byte, int):
self.arq_data_type_handler.dispatch(type_byte, received_data) self.arq_data_type_handler.dispatch(type_byte, received_data)
return return
self.log(f"Ignoring unknown transition from state {self.state.name} with frame {frame['frame_type']}") self.log(f"Ignoring unknown transition from state {self.state.name} with frame {frame['frame_type']}")

View file

@ -76,8 +76,6 @@ class ARQSessionIRS(arq_session.ARQSession):
self.received_bytes = 0 self.received_bytes = 0
self.received_crc = None self.received_crc = None
self.speed_level = 0
self.abort = False self.abort = False
def all_data_received(self): def all_data_received(self):
@ -160,16 +158,14 @@ class ARQSessionIRS(arq_session.ARQSession):
self.process_incoming_data(burst_frame) self.process_incoming_data(burst_frame)
if not self.all_data_received(): if not self.all_data_received():
downshift, upshift = self.calibrate_speed_settings() self.calibrate_speed_settings(burst_frame=burst_frame)
ack = self.frame_factory.build_arq_burst_ack( ack = self.frame_factory.build_arq_burst_ack(
self.id, self.id,
self.received_bytes, self.received_bytes,
self.speed_level, self.speed_level,
self.frames_per_burst, self.frames_per_burst,
self.snr[0], self.snr[0],
flag_abort=self.abort, flag_abort=self.abort
flag_upshift=upshift,
flag_downshift=downshift
) )
self.set_state(IRS_State.BURST_REPLY_SENT) self.set_state(IRS_State.BURST_REPLY_SENT)
@ -204,53 +200,46 @@ class ARQSessionIRS(arq_session.ARQSession):
flag_checksum=False) flag_checksum=False)
self.transmit_frame(ack, mode=FREEDV_MODE.signalling) self.transmit_frame(ack, mode=FREEDV_MODE.signalling)
self.log("CRC fail at the end of transmission!") self.log("CRC fail at the end of transmission!")
self.transmission_failed() return self.transmission_failed()
def calibrate_speed_settings(self, burst_frame=None):
if burst_frame:
received_speed_level = burst_frame['speed_level']
else:
received_speed_level = 0
def calibrate_speed_settings(self):
latest_snr = self.snr[-1] if self.snr else -10 latest_snr = self.snr[-1] if self.snr else -10
appropriate_speed_level = self.get_appropriate_speed_level(latest_snr) appropriate_speed_level = self.get_appropriate_speed_level(latest_snr)
modes_to_decode = {} modes_to_decode = {}
# Log the latest SNR, current, and appropriate speed levels for clarity # Log the latest SNR, current, appropriate speed levels, and the previous speed level
self.log( self.log(
f"Latest SNR: {latest_snr}, Current Speed Level: {self.speed_level}, Appropriate Speed Level: {appropriate_speed_level}", f"Latest SNR: {latest_snr}, Current Speed Level: {self.speed_level}, Appropriate Speed Level: {appropriate_speed_level}, Previous Speed Level: {self.previous_speed_level}",
isWarning=True) isWarning=True)
# Initialize shift flags # Adjust the speed level by one step towards the appropriate level, if needed
upshift = False
downshift = False
# Determine if we need to shift
if appropriate_speed_level > self.speed_level and self.speed_level < len(self.SPEED_LEVEL_DICT) - 1: if appropriate_speed_level > self.speed_level and self.speed_level < len(self.SPEED_LEVEL_DICT) - 1:
# Upshift by one level, but remember to listen on the current level as well in case of loosing ACK if received_speed_level == self.speed_level:
previous_speed_level = self.speed_level self.speed_level += 1
self.speed_level += 1
upshift = True
self.log(f"Upshifting. New speed level: {self.speed_level}", isWarning=True)
elif appropriate_speed_level < self.speed_level and self.speed_level > 0: elif appropriate_speed_level < self.speed_level and self.speed_level > 0:
# Downshift by one level, but remember to listen on the current level as well in case of loosing ACK if received_speed_level == self.speed_level:
previous_speed_level = self.speed_level self.speed_level -= 1
self.speed_level -= 1
downshift = True
self.log(f"Downshifting. New speed level: {self.speed_level}", isWarning=True)
else:
# No shift needed, set previous to current for correct mode decoding setup
previous_speed_level = self.speed_level
# Decode the current mode # Always decode the current mode
current_mode = self.get_mode_by_speed_level(self.speed_level).value current_mode = self.get_mode_by_speed_level(self.speed_level).value
modes_to_decode[current_mode] = True modes_to_decode[current_mode] = True
# Additionally, decode the previous speed level mode if it has changed # Decode the previous speed level mode
if upshift or downshift: if self.previous_speed_level != self.speed_level:
previous_mode = self.get_mode_by_speed_level(previous_speed_level).value previous_mode = self.get_mode_by_speed_level(self.previous_speed_level).value
modes_to_decode[previous_mode] = True modes_to_decode[previous_mode] = True
self.previous_speed_level = self.speed_level # Update the previous speed level
self.log(f"Modes to Decode: {modes_to_decode.keys()}", isWarning=True) self.log(f"Modes to Decode: {list(modes_to_decode.keys())}", isWarning=True)
# Apply the new decode mode based on the updated speed level # Apply the new decode mode based on the updated and previous speed levels
self.modem.demodulator.set_decode_mode(modes_to_decode) self.modem.demodulator.set_decode_mode(modes_to_decode)
return downshift, upshift return self.speed_level
def abort_transmission(self): def abort_transmission(self):
self.log(f"Aborting transmission... setting abort flag") self.log(f"Aborting transmission... setting abort flag")

View file

@ -68,8 +68,6 @@ class ARQSessionISS(arq_session.ARQSession):
self.frame_factory = data_frame_factory.DataFrameFactory(self.config) self.frame_factory = data_frame_factory.DataFrameFactory(self.config)
self.speed_level = 0
def generate_id(self): def generate_id(self):
while True: while True:
random_int = random.randint(1,255) random_int = random.randint(1,255)
@ -113,21 +111,34 @@ class ARQSessionISS(arq_session.ARQSession):
# Log the received frame for debugging # Log the received frame for debugging
self.log(f"Received frame: {frame}", isWarning=True) self.log(f"Received frame: {frame}", isWarning=True)
# Safely extract upshift and downshift flags with default to False if not present # Extract the speed_level directly from the frame
upshift = frame['flag'].get('UPSHIFT', False) if 'speed_level' in frame:
downshift = frame['flag'].get('DOWNSHIFT', False) new_speed_level = frame['speed_level']
# Ensure the new speed level is within the allowable range
# Check for UPSHIFT frame and ensure speed level does not exceed max limit if 0 <= new_speed_level < len(self.SPEED_LEVEL_DICT):
if upshift and not downshift and self.speed_level < len(self.SPEED_LEVEL_DICT) - 1: # Log the speed level change if it's different from the current speed level
self.speed_level += 1 if new_speed_level != self.speed_level:
self.log(f"Upshifting. New speed level: {self.speed_level}") self.log(f"Changing speed level from {self.speed_level} to {new_speed_level}", isWarning=True)
self.previous_speed_level = self.speed_level # Store the current speed level as previous
# Check for DOWNSHIFT frame and ensure speed level does not go below 0 self.speed_level = new_speed_level # Update the current speed level
elif downshift and not upshift and self.speed_level > 0: else:
self.speed_level -= 1 self.log("Received speed level is the same as the current speed level.", isWarning=True)
self.log(f"Downshifting. New speed level: {self.speed_level}") else:
self.log(f"Received speed level {new_speed_level} is out of allowable range.", isWarning=True)
else:
self.log("No speed level specified in the received frame.", isWarning=True)
# Apply the new decode mode based on the updated speed level, including the previous speed level
modes_to_decode = {
self.get_mode_by_speed_level(self.speed_level).value: True,
}
# Include the previous speed level mode if it's different from the current
if hasattr(self, 'previous_speed_level') and self.previous_speed_level != self.speed_level:
modes_to_decode[self.get_mode_by_speed_level(self.previous_speed_level).value] = True
self.log(f"Modes to Decode: {list(modes_to_decode.keys())}", isWarning=True)
# Apply the new decode mode based on the current and previous speed levels
self.modem.demodulator.set_decode_mode(modes_to_decode)
def send_info(self, irs_frame): def send_info(self, irs_frame):
# check if we received an abort flag # check if we received an abort flag
@ -174,7 +185,7 @@ class ARQSessionISS(arq_session.ARQSession):
payload = self.data[offset : offset + payload_size] payload = self.data[offset : offset + payload_size]
data_frame = self.frame_factory.build_arq_burst_frame( data_frame = self.frame_factory.build_arq_burst_frame(
self.SPEED_LEVEL_DICT[self.speed_level]["mode"], self.SPEED_LEVEL_DICT[self.speed_level]["mode"],
self.id, self.confirmed_bytes, payload) self.id, self.confirmed_bytes, payload, self.speed_level)
burst.append(data_frame) burst.append(data_frame)
self.launch_twr(burst, self.TIMEOUT_TRANSFER, self.RETRIES_CONNECT, mode='auto') self.launch_twr(burst, self.TIMEOUT_TRANSFER, self.RETRIES_CONNECT, mode='auto')
self.set_state(ISS_State.BURST_SENT) self.set_state(ISS_State.BURST_SENT)

View file

@ -15,8 +15,6 @@ class DataFrameFactory:
'FINAL': 0, # Bit-position for indicating the FINAL state 'FINAL': 0, # Bit-position for indicating the FINAL state
'ABORT': 1, # Bit-position for indicating the ABORT request 'ABORT': 1, # Bit-position for indicating the ABORT request
'CHECKSUM': 2, # Bit-position for indicating the CHECKSUM is correct or not 'CHECKSUM': 2, # Bit-position for indicating the CHECKSUM is correct or not
'DOWNSHIFT': 3, # Bit-position for indicating a requested ARQ DOWNSHIFT
'UPSHIFT': 4, # Bit-position for indicating a requested ARQ UPSHIFT
} }
def __init__(self, config): def __init__(self, config):
@ -146,6 +144,7 @@ class DataFrameFactory:
self.template_list[FR_TYPE.ARQ_BURST_FRAME.value] = { self.template_list[FR_TYPE.ARQ_BURST_FRAME.value] = {
"frame_length": None, "frame_length": None,
"session_id": 1, "session_id": 1,
"speed_level": 1,
"offset": 4, "offset": 4,
"data": "dynamic", "data": "dynamic",
} }
@ -396,9 +395,10 @@ class DataFrameFactory:
} }
return self.construct(FR_TYPE.ARQ_SESSION_INFO_ACK, payload) return self.construct(FR_TYPE.ARQ_SESSION_INFO_ACK, payload)
def build_arq_burst_frame(self, freedv_mode: codec2.FREEDV_MODE, session_id: int, offset: int, data: bytes): def build_arq_burst_frame(self, freedv_mode: codec2.FREEDV_MODE, session_id: int, offset: int, data: bytes, speed_level: int):
payload = { payload = {
"session_id": session_id.to_bytes(1, 'big'), "session_id": session_id.to_bytes(1, 'big'),
"speed_level": speed_level.to_bytes(4, 'big'),
"offset": offset.to_bytes(4, 'big'), "offset": offset.to_bytes(4, 'big'),
"data": data, "data": data,
} }
@ -406,7 +406,7 @@ class DataFrameFactory:
return frame return frame
def build_arq_burst_ack(self, session_id: bytes, offset, speed_level: int, def build_arq_burst_ack(self, session_id: bytes, offset, speed_level: int,
frames_per_burst: int, snr: int, flag_final=False, flag_checksum=False, flag_abort=False, flag_downshift=False, flag_upshift=False): frames_per_burst: int, snr: int, flag_final=False, flag_checksum=False, flag_abort=False):
flag = 0b00000000 flag = 0b00000000
if flag_final: if flag_final:
flag = helpers.set_flag(flag, 'FINAL', True, self.ARQ_FLAGS) flag = helpers.set_flag(flag, 'FINAL', True, self.ARQ_FLAGS)
@ -417,14 +417,6 @@ class DataFrameFactory:
if flag_abort: if flag_abort:
flag = helpers.set_flag(flag, 'ABORT', True, self.ARQ_FLAGS) flag = helpers.set_flag(flag, 'ABORT', True, self.ARQ_FLAGS)
if flag_downshift:
flag = helpers.set_flag(flag, 'DOWNSHIFT', True, self.ARQ_FLAGS)
flag = helpers.set_flag(flag, 'UPSHIFT', False, self.ARQ_FLAGS)
if flag_upshift:
flag = helpers.set_flag(flag, 'DOWNSHIFT', False, self.ARQ_FLAGS)
flag = helpers.set_flag(flag, 'UPSHIFT', True, self.ARQ_FLAGS)
payload = { payload = {
"session_id": session_id.to_bytes(1, 'big'), "session_id": session_id.to_bytes(1, 'big'),
"offset": offset.to_bytes(4, 'big'), "offset": offset.to_bytes(4, 'big'),