From 8b318e5bc5ffdebf757bf533a29162d40dc4a0b6 Mon Sep 17 00:00:00 2001 From: Dan Smith Date: Fri, 31 Jan 2025 14:43:26 -0800 Subject: [PATCH] anytone: Add PTTID setting Fixes: #11798 --- chirp/bitwise.py | 24 +++++++++++++++++++++++- chirp/drivers/anytone.py | 29 +++++++++++++++++++++++++++++ 2 files changed, 52 insertions(+), 1 deletion(-) diff --git a/chirp/bitwise.py b/chirp/bitwise.py index 1c9c29af..53581bd8 100644 --- a/chirp/bitwise.py +++ b/chirp/bitwise.py @@ -161,7 +161,29 @@ def int_to_bcd(bcd_array, value): """Convert an int like 1234 into bcdDataElements like "\x12\x34" """ for i in reversed(range(0, len(bcd_array))): bcd_array[i].set_value(value % 100) - value /= 100 + value //= 100 + + +def numeric_str_to_bcd(bcdel, string, pad='0'): + """Convert a string of digits into BCD-like bytes. + + This should only be used for the quasi-BCD encodings of DTMF characters + that some radios use (i.e. 0x12 == "12" and 0x1D == "1D") + """ + string = string.ljust(2 * bcdel.size() // 8, pad) + for i in range(0, bcdel.size() // 8): + bcdel[i] = int(string[i*2:i*2+2], 16) + + +def bcd_to_numeric_str(bcdel, pad='0'): + """Convert a list of BCD-like bytes into a string. + + See numeric_str_to_bcd above. + """ + string = '' + for i in range(0, bcdel.size() // 8): + string += '%02X' % bcdel[i] + return string.ljust(2 * bcdel.size() // 8, pad) def get_string(char_array): diff --git a/chirp/drivers/anytone.py b/chirp/drivers/anytone.py index 4526382b..d619e0df 100644 --- a/chirp/drivers/anytone.py +++ b/chirp/drivers/anytone.py @@ -132,6 +132,13 @@ char welcome[8]; } settings; +#seekto 0x0400; +struct { + u8 code[12]; + u8 len; + u8 unknown2[3]; +} dtmf_codes[16]; + #seekto 0x0540; struct memory memblk1[12]; @@ -707,11 +714,33 @@ def filter(s): current_index=_settings.mute)) basic.append(rs) + dtmf = RadioSettingGroup('dtmf', 'DTMF') + for i in range(16): + length = int(self._memobj.dtmf_codes[i].len) + val = bitwise.bcd_to_numeric_str(self._memobj.dtmf_codes[i].code) + val = val[:length] + val = val.replace('E', '*').replace('F', '#') + rs = RadioSetting('dtmf%i' % i, 'DTMF M%i' % (i + 1), + RadioSettingValueString( + 0, 24, + val, autopad=False, + charset='01234567890*#abcdABCD')) + dtmf.append(rs) + + settings.append(dtmf) return settings def set_settings(self, settings): _settings = self._memobj.settings for element in settings: + if element.get_name() == 'dtmf': + for i in range(16): + val = str(element['dtmf%i' % i].value).strip() + val = val.replace('*', 'E').replace('#', 'F') + self._memobj.dtmf_codes[i].len = len(val) + bitwise.numeric_str_to_bcd( + self._memobj.dtmf_codes[i].code, val) + continue if not isinstance(element, RadioSetting): self.set_settings(element) continue