Add FEC type to station heard line.

This commit is contained in:
wb2osz 2023-09-11 00:07:36 +01:00
parent 7a8e4320ac
commit a08d0939b5
10 changed files with 80 additions and 59 deletions

View File

@ -757,7 +757,7 @@ int audio_get (int a)
* This is called when we have a good frame.
*/
void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, int is_fx25, retry_t retries, char *spectrum)
void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, fec_type_t fec_type, retry_t retries, char *spectrum)
{
char stemp[500];
@ -826,29 +826,31 @@ void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alev
strlcat (heard, ")", sizeof(heard));
}
switch (fec_type) {
case fec_type_fx25:
dw_printf ("%s audio level = %s FX.25 %s\n", heard, alevel_text, spectrum);
break;
case fec_type_il2p:
dw_printf ("%s audio level = %s IL2P %s\n", heard, alevel_text, spectrum);
break;
case fec_type_none:
default:
if (my_audio_config.achan[chan].fix_bits == RETRY_NONE && my_audio_config.achan[chan].passall == 0) {
dw_printf ("%s audio level = %s %s\n", heard, alevel_text, spectrum);
}
else if (is_fx25) {
// No fix_bits or passall specified.
dw_printf ("%s audio level = %s %s\n", heard, alevel_text, spectrum);
}
else {
assert (retries >= RETRY_NONE && retries <= RETRY_MAX);
assert (retries >= RETRY_NONE && retries <= RETRY_MAX); // validate array index.
dw_printf ("%s audio level = %s [%s] %s\n", heard, alevel_text, retry_text[(int)retries], spectrum);
}
break;
}
#endif
//#if defined(EXPERIMENT_G) || defined(EXPERIMENT_H)
// int j;
//
// for (j=0; j<MAX_SUBCHANS; j++) {
// if (spectrum[j] == '|') {
// count[j]++;
// }
// }
//#endif
// Display non-APRS packets in a different color.

View File

@ -128,6 +128,7 @@
#include "il2p.h"
#include "dwsock.h"
#include "dns_sd_dw.h"
#include "dlq.h" // for fec_type_t definition.
//static int idx_decoded = 0;
@ -300,7 +301,7 @@ int main (int argc, char *argv[])
text_color_init(t_opt);
text_color_set(DW_COLOR_INFO);
dw_printf ("Dire Wolf version %d.%d (%s) BETA TEST 5\n", MAJOR_VERSION, MINOR_VERSION, __DATE__);
dw_printf ("Dire Wolf version %d.%d (%s) BETA TEST 7\n", MAJOR_VERSION, MINOR_VERSION, __DATE__);
//dw_printf ("Dire Wolf DEVELOPMENT version %d.%d %s (%s)\n", MAJOR_VERSION, MINOR_VERSION, "G", __DATE__);
//dw_printf ("Dire Wolf version %d.%d\n", MAJOR_VERSION, MINOR_VERSION);
@ -1179,7 +1180,7 @@ int main (int argc, char *argv[])
// TODO: Use only one printf per line so output doesn't get jumbled up with stuff from other threads.
void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, int is_fx25, retry_t retries, char *spectrum)
void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, fec_type_t fec_type, retry_t retries, char *spectrum)
{
char stemp[500];
@ -1188,7 +1189,8 @@ void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alev
char heard[AX25_MAX_ADDR_LEN];
//int j;
int h;
char display_retries[32];
char display_retries[32]; // Extra stuff before slice indicators.
// Can indicate FX.25/IL2P or fix_bits.
assert (chan >= 0 && chan < MAX_TOTAL_CHANS); // TOTAL for virtual channels
assert (subchan >= -2 && subchan < MAX_SUBCHANS);
@ -1197,13 +1199,22 @@ void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alev
strlcpy (display_retries, "", sizeof(display_retries));
if (is_fx25) {
;
}
else if (audio_config.achan[chan].fix_bits != RETRY_NONE || audio_config.achan[chan].passall) {
switch (fec_type) {
case fec_type_fx25:
strlcpy (display_retries, " FX.25 ", sizeof(display_retries));
break;
case fec_type_il2p:
strlcpy (display_retries, " IL2P ", sizeof(display_retries));
break;
case fec_type_none:
default:
// Possible fix_bits indication.
if (audio_config.achan[chan].fix_bits != RETRY_NONE || audio_config.achan[chan].passall) {
assert (retries >= RETRY_NONE && retries <= RETRY_MAX);
snprintf (display_retries, sizeof(display_retries), " [%s] ", retry_text[(int)retries]);
}
break;
}
ax25_format_addrs (pp, stemp);
@ -1567,7 +1578,7 @@ void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alev
* However, if it used FEC mode (FX.25. IL2P), we have much higher level of
* confidence that it is correct.
*/
if (ax25_is_aprs(pp) && ( retries == RETRY_NONE || is_fx25) ) {
if (ax25_is_aprs(pp) && ( retries == RETRY_NONE || fec_type == fec_type_fx25 || fec_type == fec_type_il2p) ) {
igate_send_rec_packet (chan, pp);
}
@ -1588,7 +1599,7 @@ void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alev
* However, if it used FEC mode (FX.25. IL2P), we have much higher level of
* confidence that it is correct.
*/
if (ax25_is_aprs(pp) && ( retries == RETRY_NONE || is_fx25) ) {
if (ax25_is_aprs(pp) && ( retries == RETRY_NONE || fec_type == fec_type_fx25 || fec_type == fec_type_il2p) ) {
digipeater (chan, pp);
}
@ -1598,7 +1609,7 @@ void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alev
* Use only those with correct CRC (or using FEC.)
*/
if (retries == RETRY_NONE || is_fx25) {
if (retries == RETRY_NONE || fec_type == fec_type_fx25 || fec_type == fec_type_il2p) {
cdigipeater (chan, pp);
}

View File

@ -215,10 +215,10 @@ void dlq_init (void)
* display of audio level line.
* Use -2 to indicate DTMF message.)
*
* is_fx25 - Was it from FX.25? Need to know because
* fec_type - Was it from FX.25 or IL2P? Need to know because
* meaning of retries is different.
*
* retries - Level of bit correction used.
* retries - Level of correction used.
*
* spectrum - Display of how well multiple decoders did.
*
@ -228,7 +228,7 @@ void dlq_init (void)
*
*--------------------------------------------------------------------*/
void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, int is_fx25, retry_t retries, char *spectrum)
void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, fec_type_t fec_type, retry_t retries, char *spectrum)
{
struct dlq_item_s *pnew;
@ -278,7 +278,7 @@ void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alev
pnew->subchan = subchan;
pnew->pp = pp;
pnew->alevel = alevel;
pnew->is_fx25 = is_fx25;
pnew->fec_type = fec_type;
pnew->retries = retries;
if (spectrum == NULL)
strlcpy(pnew->spectrum, "", sizeof(pnew->spectrum));

View File

@ -33,10 +33,13 @@ typedef struct cdata_s {
/* Types of things that can be in queue. */
typedef enum dlq_type_e {DLQ_REC_FRAME, DLQ_CONNECT_REQUEST, DLQ_DISCONNECT_REQUEST, DLQ_XMIT_DATA_REQUEST, DLQ_REGISTER_CALLSIGN, DLQ_UNREGISTER_CALLSIGN, DLQ_OUTSTANDING_FRAMES_REQUEST, DLQ_CHANNEL_BUSY, DLQ_SEIZE_CONFIRM, DLQ_CLIENT_CLEANUP} dlq_type_t;
typedef enum fec_type_e {fec_type_none=0, fec_type_fx25=1, fec_type_il2p=2} fec_type_t;
/* A queue item. */
@ -68,7 +71,7 @@ typedef struct dlq_item_s {
alevel_t alevel; /* Audio level. */
int is_fx25; /* Was it from FX.25? */
fec_type_t fec_type; // Type of FEC for received signal: none, FX.25, or IL2P.
retry_t retries; /* Effort expended to get a valid CRC. */
/* Bits changed for regular AX.25. */
@ -106,7 +109,7 @@ void dlq_init (void);
void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, int is_fx25, retry_t retries, char *spectrum);
void dlq_rec_frame (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, fec_type_t fec_type, retry_t retries, char *spectrum);
void dlq_connect_request (char addrs[AX25_MAX_ADDRS][AX25_MAX_ADDR_LEN], int num_addr, int chan, int client, int pid);

View File

@ -6,6 +6,7 @@
#include "ax25_pad.h" /* for packet_t, alevel_t */
#include "rrbb.h"
#include "audio.h" /* for struct audio_s */
#include "dlq.h" // for fec_type_t definition.
@ -62,6 +63,6 @@ int hdlc_rec2_try_to_fix_later (rrbb_t block, int chan, int subchan, int slice,
/* Provided by the top level application to process a complete frame. */
void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t level, int is_fx25, retry_t retries, char *spectrum);
void app_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t level, fec_type_t fec_type, retry_t retries, char *spectrum);
#endif

View File

@ -1564,9 +1564,9 @@ static void * igate_recv_thread (void *arg)
// See what happens with -2 and follow up on this.
// Do we need something else here?
int slice = 0;
int is_fx25 = 0;
fec_type_t fec_type = fec_type_none;
char spectrum[] = "APRS-IS";
dlq_rec_frame (ichan, subchan, slice, pp3, alevel, is_fx25, RETRY_NONE, spectrum);
dlq_rec_frame (ichan, subchan, slice, pp3, alevel, fec_type, RETRY_NONE, spectrum);
}
else {
text_color_set(DW_COLOR_ERROR);

View File

@ -943,7 +943,7 @@ void tone_gen_put_bit (int chan, int data)
// This is called when a complete frame has been deserialized.
void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, int is_fx25)
void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, fec_type_t fec_type)
{
if (rec_count < 0) return; // Skip check before serdes test.

View File

@ -116,7 +116,8 @@ static struct audio_s *save_audio_config_p;
static struct {
packet_t packet_p;
alevel_t alevel;
int is_fx25; // 1 for FX.25, 0 for regular AX.25.
float speed_error;
fec_type_t fec_type; // Type of FEC: none(0), fx25, il2p
retry_t retries; // For the old "fix bits" strategy, this is the
// number of bits that were modified to get a good CRC.
// It would be 0 to something around 4.
@ -306,14 +307,14 @@ void multi_modem_process_sample (int chan, int audio_sample)
* display of audio level line.
* Use -2 to indicate DTMF message.)
* retries - Level of correction used.
* is_fx25 - 1 for FX.25, 0 for normal AX.25.
* fec_type - none(0), fx25, il2p
*
* Description: Add to list of candidates. Best one will be picked later.
*
*--------------------------------------------------------------------*/
void multi_modem_process_rec_frame (int chan, int subchan, int slice, unsigned char *fbuf, int flen, alevel_t alevel, retry_t retries, int is_fx25)
void multi_modem_process_rec_frame (int chan, int subchan, int slice, unsigned char *fbuf, int flen, alevel_t alevel, retry_t retries, fec_type_t fec_type)
{
packet_t pp;
@ -346,12 +347,12 @@ void multi_modem_process_rec_frame (int chan, int subchan, int slice, unsigned c
pp = ax25_from_frame (fbuf, flen, alevel);
}
multi_modem_process_rec_packet (chan, subchan, slice, pp, alevel, retries, is_fx25);
multi_modem_process_rec_packet (chan, subchan, slice, pp, alevel, retries, fec_type);
}
// TODO: Eliminate function above and move code elsewhere?
void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, int is_fx25)
void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, fec_type_t fec_type)
{
if (pp == NULL) {
text_color_set(DW_COLOR_ERROR);
@ -386,7 +387,7 @@ void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t
ax25_delete (pp);
}
else {
dlq_rec_frame (chan, subchan, slice, pp, alevel, is_fx25, retries, "");
dlq_rec_frame (chan, subchan, slice, pp, alevel, fec_type, retries, "");
}
return;
}
@ -406,7 +407,7 @@ void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t
candidate[chan][subchan][slice].packet_p = pp;
candidate[chan][subchan][slice].alevel = alevel;
candidate[chan][subchan][slice].is_fx25 = is_fx25;
candidate[chan][subchan][slice].fec_type = fec_type;
candidate[chan][subchan][slice].retries = retries;
candidate[chan][subchan][slice].age = 0;
candidate[chan][subchan][slice].crc = ax25_m_m_crc(pp);
@ -443,6 +444,9 @@ static void pick_best_candidate (int chan)
int best_n, best_score;
char spectrum[MAX_SUBCHANS*MAX_SLICERS+1];
int n, j, k;
if (save_audio_config_p->achan[chan].num_slicers < 1) {
save_audio_config_p->achan[chan].num_slicers = 1;
}
int num_bars = save_audio_config_p->achan[chan].num_slicers * save_audio_config_p->achan[chan].num_subchan;
memset (spectrum, 0, sizeof(spectrum));
@ -456,7 +460,7 @@ static void pick_best_candidate (int chan)
if (candidate[chan][j][k].packet_p == NULL) {
spectrum[n] = '_';
}
else if (candidate[chan][j][k].is_fx25) {
else if (candidate[chan][j][k].fec_type != fec_type_none) { // FX.25 or IL2P
// FIXME: using retries both as an enum and later int too.
if ((int)(candidate[chan][j][k].retries) <= 9) {
spectrum[n] = '0' + candidate[chan][j][k].retries;
@ -464,7 +468,7 @@ static void pick_best_candidate (int chan)
else {
spectrum[n] = '+';
}
}
} // AX.25 below
else if (candidate[chan][j][k].retries == RETRY_NONE) {
spectrum[n] = '|';
}
@ -481,8 +485,8 @@ static void pick_best_candidate (int chan)
candidate[chan][j][k].score = 0;
}
else {
if (candidate[chan][j][k].is_fx25) {
candidate[chan][j][k].score = 9000 - 100 * candidate[chan][j][k].retries;
if (candidate[chan][j][k].fec_type != fec_type_none) {
candidate[chan][j][k].score = 9000 - 100 * candidate[chan][j][k].retries; // has FEC
}
else {
/* Originally, this produced 0 for the PASSALL case. */
@ -550,9 +554,9 @@ static void pick_best_candidate (int chan)
candidate[chan][j][k].packet_p);
}
else {
dw_printf ("%d.%d.%d: ptr=%p, is_fx25=%d, retry=%d, age=%3d, crc=%04x, score=%d %s\n", chan, j, k,
dw_printf ("%d.%d.%d: ptr=%p, fec_type=%d, retry=%d, age=%3d, crc=%04x, score=%d %s\n", chan, j, k,
candidate[chan][j][k].packet_p,
candidate[chan][j][k].is_fx25,
(int)(candidate[chan][j][k].fec_type),
(int)(candidate[chan][j][k].retries),
candidate[chan][j][k].age,
candidate[chan][j][k].crc,
@ -611,7 +615,7 @@ static void pick_best_candidate (int chan)
dlq_rec_frame (chan, j, k,
candidate[chan][j][k].packet_p,
candidate[chan][j][k].alevel,
candidate[chan][j][k].is_fx25,
candidate[chan][j][k].fec_type,
(int)(candidate[chan][j][k].retries),
spectrum);

View File

@ -17,8 +17,8 @@ void multi_modem_process_sample (int c, int audio_sample);
int multi_modem_get_dc_average (int chan);
// Deprecated. Replace with ...packet
void multi_modem_process_rec_frame (int chan, int subchan, int slice, unsigned char *fbuf, int flen, alevel_t alevel, retry_t retries, int is_fx25);
void multi_modem_process_rec_frame (int chan, int subchan, int slice, unsigned char *fbuf, int flen, alevel_t alevel, retry_t retries, fec_type_t fec_type);
void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, int is_fx25);
void multi_modem_process_rec_packet (int chan, int subchan, int slice, packet_t pp, alevel_t alevel, retry_t retries, fec_type_t fec_type);
#endif

View File

@ -339,7 +339,7 @@ void recv_process (void)
* - Digipeater.
*/
app_process_rec_packet (pitem->chan, pitem->subchan, pitem->slice, pitem->pp, pitem->alevel, pitem->is_fx25, pitem->retries, pitem->spectrum);
app_process_rec_packet (pitem->chan, pitem->subchan, pitem->slice, pitem->pp, pitem->alevel, pitem->fec_type, pitem->retries, pitem->spectrum);
/*