From ea645c306150242314575f759373eec3dacf0d91 Mon Sep 17 00:00:00 2001 From: KubaPro010 Date: Mon, 14 Apr 2025 16:19:08 +0200 Subject: [PATCH] change some ascii logic, reduce source code size, redo some functions and add another way to save rdsmodulator data (this one needs both enc and mod data refresh) --- src/ascii_cmd.c | 174 ++++++++----------------- src/lib.c | 29 ++--- src/lib.h | 2 +- src/modulator.c | 67 ++++++---- src/modulator.h | 7 + src/rds.c | 333 ++++++++++++++++++++---------------------------- src/rds.h | 10 +- 7 files changed, 253 insertions(+), 369 deletions(-) diff --git a/src/ascii_cmd.c b/src/ascii_cmd.c index ad5b1d4..e95da9a 100644 --- a/src/ascii_cmd.c +++ b/src/ascii_cmd.c @@ -17,26 +17,26 @@ typedef struct { } pattern_command_handler_t; static void handle_ptyn(char *arg, RDSModulator* mod, char* output) { - arg[PTYN_LENGTH * 2] = 0; - set_rds_ptyn(mod->enc, convert_to_rds_charset(arg)); + arg[PTYN_LENGTH+1] = 0; + set_rds_ptyn(mod->enc, convert_to_rdscharset(arg)); strcpy(output, "+\0"); } static void handle_tps(char *arg, RDSModulator* mod, char* output) { - arg[PS_LENGTH * 2] = 0; - set_rds_tps(mod->enc, convert_to_rds_charset(arg)); + arg[PS_LENGTH+1] = 0; + set_rds_tps(mod->enc, convert_to_rdscharset(arg)); strcpy(output, "+\0"); } static void handle_rt1(char *arg, RDSModulator* mod, char* output) { - arg[RT_LENGTH * 2] = 0; - set_rds_rt1(mod->enc, convert_to_rds_charset(arg)); + arg[RT_LENGTH+1] = 0; + set_rds_rt1(mod->enc, convert_to_rdscharset(arg)); strcpy(output, "+\0"); } static void handle_rt2(char *arg, RDSModulator* mod, char* output) { - arg[RT_LENGTH * 2] = 0; - set_rds_rt2(mod->enc, convert_to_rds_charset(arg)); + arg[RT_LENGTH+1] = 0; + set_rds_rt2(mod->enc, convert_to_rdscharset(arg)); strcpy(output, "+\0"); } @@ -56,9 +56,7 @@ static void handle_rtp(char *arg, RDSModulator* mod, char* output) { if (sscanf((char *)arg, "%hhu,%hhu,%hhu,%hhu,%hhu,%hhu", &tags[0], &tags[1], &tags[2], &tags[3], &tags[4], &tags[5]) == 6) { set_rds_rtplus_tags(mod->enc, tags); strcpy(output, "+\0"); - } else { - strcpy(output, "-\0"); - } + } else strcpy(output, "-\0"); } static void handle_ertp(char *arg, RDSModulator* mod, char* output) { @@ -67,9 +65,7 @@ static void handle_ertp(char *arg, RDSModulator* mod, char* output) { if (sscanf((char *)arg, "%hhu,%hhu,%hhu,%hhu,%hhu,%hhu", &tags[0], &tags[1], &tags[2], &tags[3], &tags[4], &tags[5]) == 6) { set_rds_ertplus_tags(mod->enc, tags); strcpy(output, "+\0"); - } else { - strcpy(output, "-\0"); - } + } else strcpy(output, "-\0"); } static void handle_link(char *arg, RDSModulator* mod, char* output) { @@ -83,20 +79,20 @@ static void handle_link(char *arg, RDSModulator* mod, char* output) { } static void handle_lps(char *arg, RDSModulator* mod, char* output) { - arg[LPS_LENGTH * 2] = 0; + arg[LPS_LENGTH+1] = 0; set_rds_lps(mod->enc, arg); strcpy(output, "+\0"); } static void handle_ert(char *arg, RDSModulator* mod, char* output) { - arg[ERT_LENGTH * 2] = 0; + arg[ERT_LENGTH+1] = 0; set_rds_ert(mod->enc, arg); strcpy(output, "+\0"); } static void handle_ps(char *arg, RDSModulator* mod, char* output) { - arg[PS_LENGTH * 2] = 0; - set_rds_ps(mod->enc, convert_to_rds_charset(arg)); + arg[PS_LENGTH+1] = 0; + set_rds_ps(mod->enc, convert_to_rdscharset(arg)); strcpy(output, "+\0"); } @@ -136,10 +132,6 @@ static void handle_pi(char *arg, RDSModulator* mod, char* output) { } static void handle_af(char *arg, RDSModulator* mod, char* output) { - if (arg[0] == 'A' || arg[0] == 'B') { - strcpy(output, "-\0"); - return; - } if(arg[0] == '\0') { memset(&(mod->enc->data[mod->enc->program].af), 0, sizeof(mod->enc->data[mod->enc->program].af)); return; @@ -174,10 +166,6 @@ static void handle_af(char *arg, RDSModulator* mod, char* output) { } static void handle_afo(char *arg, RDSModulator* mod, char* output) { - if (arg[0] == 'A' || arg[0] == 'B') { - strcpy(output, "-\0"); - return; - } if(arg[0] == '\0') { memset(&(mod->enc->data[mod->enc->program].af_oda), 0, sizeof(mod->enc->data[mod->enc->program].af_oda)); return; @@ -242,7 +230,7 @@ static void handle_rt2en(char *arg, RDSModulator* mod, char* output) { static void handle_rtper(char *arg, RDSModulator* mod, char* output) { mod->enc->data[mod->enc->program].rt_switching_period = atoi(arg); - mod->enc->data[mod->enc->program].orignal_rt_switching_period = mod->enc->data[mod->enc->program].rt_switching_period; + mod->enc->state[mod->enc->program].rt_switching_period_state = mod->enc->data[mod->enc->program].rt_switching_period; strcpy(output, "+\0"); } @@ -256,9 +244,7 @@ static void handle_rtprun(char *arg, RDSModulator* mod, char* output) { if (sscanf(arg, "%d,%d", &flag1, &flag2) == 2) { set_rds_rtplus_flags(mod->enc, flag1); if(flag2) mod->enc->rtpState[mod->enc->program][0].toggle ^= 1; - } else { - set_rds_rtplus_flags(mod->enc, atoi(arg)); - } + } else set_rds_rtplus_flags(mod->enc, atoi(arg)); strcpy(output, "+\0"); } @@ -267,9 +253,7 @@ static void handle_ertprun(char *arg, RDSModulator* mod, char* output) { if (sscanf(arg, "%d,%d", &flag1, &flag2) == 2) { set_rds_ertplus_flags(mod->enc, flag1); if(flag2) mod->enc->rtpState[mod->enc->program][1].toggle ^= 1; - } else { - set_rds_ertplus_flags(mod->enc, atoi(arg)); - } + } else set_rds_ertplus_flags(mod->enc, atoi(arg)); strcpy(output, "+\0"); } @@ -293,19 +277,13 @@ static void handle_rds2mod(char *arg, RDSModulator* mod, char* output) { } static void handle_grpseq(char *arg, RDSModulator* mod, char* output) { - if (arg[0] == '\0') { - set_rds_grpseq(mod->enc, DEFAULT_GRPSQC); - } else { - set_rds_grpseq(mod->enc, arg); - } + if (arg[0] == '\0') set_rds_grpseq(mod->enc, DEFAULT_GRPSQC); + else set_rds_grpseq(mod->enc, arg); strcpy(output, "+\0"); } static void handle_grpseq2(char *arg, RDSModulator* mod, char* output) { - if (arg[0] == '\0') { - set_rds_grpseq2(mod->enc, "\0"); - } else { - set_rds_grpseq2(mod->enc, arg); - } + if (arg[0] == '\0') set_rds_grpseq2(mod->enc, "\0"); + else set_rds_grpseq2(mod->enc, arg); strcpy(output, "+\0"); } @@ -323,9 +301,7 @@ static void handle_level(char *arg, RDSModulator* mod, char* output) { static void handle_reset(char *arg, RDSModulator* mod, char* output) { (void)arg; loadFromFile(mod->enc); - for(int i = 0; i < PROGRAMS; i++) { - reset_rds_state(mod->enc, i); - } + for(int i = 0; i < PROGRAMS; i++) reset_rds_state(mod->enc, i); Modulator_loadFromFile(&mod->params); strcpy(output, "\0"); } @@ -342,23 +318,15 @@ static void handle_udg(char *arg, char *pattern, RDSModulator* mod, char* output char *ptr = arg; while (sets < 8) { - int count = sscanf((char *)ptr, "%4hx%4hx%4hx", - &blocks[sets][0], &blocks[sets][1], &blocks[sets][2]); - + int count = sscanf((char *)ptr, "%4hx%4hx%4hx", &blocks[sets][0], &blocks[sets][1], &blocks[sets][2]); if (count != 3) { all_scanned = 0; break; } - sets++; - - while (*ptr && *ptr != ',') { - ptr++; - } - - if (*ptr == ',') { - ptr++; - } else { + while (*ptr && *ptr != ',') ptr++; + if (*ptr == ',') ptr++; + else { bad_format = 1; break; } @@ -370,9 +338,7 @@ static void handle_udg(char *arg, char *pattern, RDSModulator* mod, char* output } else if(strcmp(pattern, "2") == 0) { memcpy(&(mod->enc->data[mod->enc->program].udg2), &blocks, sets * sizeof(uint16_t[3])); mod->enc->data[mod->enc->program].udg2_len = sets; - } else { - strcpy(output, "!\0"); - } + } else strcpy(output, "!\0"); if(bad_format) strcpy(output, "-\0"); else if(all_scanned) strcpy(output, "+\0"); else strcpy(output, "/\0"); @@ -392,7 +358,7 @@ static void handle_init(char *arg, RDSModulator* mod, char* output) { static void handle_ver(char *arg, RDSModulator* mod, char* output) { (void)arg; (void)mod; - sprintf(output, "Encoder v. %s - (C) 2025 radio95", VERSION); + sprintf(output, "RDS95 v. %s - (C) 2025 radio95", VERSION); } static void handle_eonen(char *arg, char *pattern, RDSModulator* mod, char* output) { @@ -413,7 +379,7 @@ static void handle_eonps(char *arg, char *pattern, RDSModulator* mod, char* outp uint16_t len = 0; while (*arg != 0 && len < 24) eon->ps[len++] = *arg++; - + strcpy(output, "+\0"); } @@ -423,7 +389,7 @@ static void handle_eonpty(char *arg, char *pattern, RDSModulator* mod, char* out } static void handle_eonta(char *arg, char *pattern, RDSModulator* mod, char* output) { - if (!mod->enc->data[mod->enc->program].eon[atoi(pattern)-1].enabled || + if (!mod->enc->data[mod->enc->program].eon[atoi(pattern)-1].enabled || !mod->enc->data[mod->enc->program].eon[atoi(pattern)-1].tp) { strcpy(output, "-\0"); return; @@ -538,7 +504,6 @@ static const command_handler_t commands_exact[] = { {"INIT", handle_init, 4}, {"VER", handle_ver, 3}, {"RESET", handle_reset, 5}, - // TODO: handle help, status }; static const pattern_command_handler_t pattern_commands[] = { @@ -567,49 +532,38 @@ static bool process_command_table(const command_handler_t *table, int table_size static bool process_pattern_commands(char *cmd, char *arg, char *output, RDSModulator* mod) { size_t cmd_len = strlen(cmd); char pattern_buffer[16] = {0}; - for (size_t i = 0; i < sizeof(pattern_commands) / sizeof(pattern_command_handler_t); i++) { const pattern_command_handler_t *handler = &pattern_commands[i]; size_t prefix_len = strlen(handler->prefix); size_t suffix_len = strlen(handler->suffix); - - if (cmd_len > (prefix_len + suffix_len) && - strncmp(cmd, handler->prefix, prefix_len) == 0 && - strcmp(cmd + cmd_len - suffix_len, handler->suffix) == 0) { - + if (cmd_len > (prefix_len + suffix_len) && strncmp(cmd, handler->prefix, prefix_len) == 0 && strcmp(cmd + cmd_len - suffix_len, handler->suffix) == 0) { size_t pattern_len = cmd_len - prefix_len - suffix_len; if (pattern_len < sizeof(pattern_buffer)) { strncpy(pattern_buffer, cmd + prefix_len, pattern_len); pattern_buffer[pattern_len] = 0; - handler->handler(arg, pattern_buffer, mod, output); return true; } } } - return false; } void process_ascii_cmd(RDSModulator* mod, char *str, char *cmd_output) { char *cmd, *arg; + char output[255]; memset(output, 0, sizeof(output)); + char upper_str[CTL_BUFFER_SIZE]; - uint16_t cmd_len = _strnlen((const char*)str, CTL_BUFFER_SIZE); - - for(uint16_t i = 0; i < cmd_len; i++) { - if(str[i] == '\t') str[i] = ' '; - } + for(uint16_t i = 0; i < cmd_len; i++) if(str[i] == '\t') str[i] = ' '; strncpy(upper_str, str, CTL_BUFFER_SIZE); upper_str[CTL_BUFFER_SIZE-1] = '\0'; for(uint16_t i = 0; i < cmd_len && upper_str[i] != '='; i++) { - if(upper_str[i] >= 'a' && upper_str[i] <= 'z') { - upper_str[i] = upper_str[i] - 'a' + 'A'; - } + if(upper_str[i] >= 'a' && upper_str[i] <= 'z') upper_str[i] = upper_str[i] - 'a' + 'A'; } for (size_t i = 0; i < sizeof(commands_exact) / sizeof(command_handler_t); i++) { @@ -624,8 +578,7 @@ void process_ascii_cmd(RDSModulator* mod, char *str, char *cmd_output) { const char* option_str = upper_str + 1; char option[32] = {0}; size_t copy_len = strlen(option_str); - if (copy_len >= sizeof(option)) - copy_len = sizeof(option) - 1; + if (copy_len >= sizeof(option)) copy_len = sizeof(option) - 1; memcpy(option, option_str, copy_len); option[copy_len] = '\0'; saveToFile(mod->enc, option); @@ -638,86 +591,67 @@ void process_ascii_cmd(RDSModulator* mod, char *str, char *cmd_output) { cmd = upper_str; cmd[equals_pos - upper_str] = 0; arg = equals_pos + 1; - process_pattern_commands(cmd, arg, output, mod); } + uint8_t cmd_reached = 0; + if (cmd_len > 1 && str[1] == '=') { cmd = upper_str; cmd[1] = 0; arg = str + 2; - - if (process_command_table(commands_eq2, - sizeof(commands_eq2) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq2, sizeof(commands_eq2) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } if (cmd_len > 2 && str[2] == '=') { cmd = upper_str; cmd[2] = 0; arg = str + 3; - - if (process_command_table(commands_eq3, - sizeof(commands_eq3) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq3, sizeof(commands_eq3) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } if (cmd_len > 3 && str[3] == '=') { cmd = upper_str; cmd[3] = 0; arg = str + 4; - - if (process_command_table(commands_eq4, - sizeof(commands_eq4) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq4, sizeof(commands_eq4) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } if (cmd_len > 4 && str[4] == '=') { cmd = upper_str; cmd[4] = 0; arg = str + 5; - - if (process_command_table(commands_eq5, - sizeof(commands_eq5) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq5, sizeof(commands_eq5) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } if (cmd_len > 5 && str[5] == '=') { cmd = upper_str; cmd[5] = 0; arg = str + 6; - - if (process_command_table(commands_eq6, - sizeof(commands_eq6) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq6, sizeof(commands_eq6) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } if (cmd_len > 6 && str[6] == '=') { cmd = upper_str; cmd[6] = 0; arg = str + 7; - - if (process_command_table(commands_eq7, - sizeof(commands_eq7) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq7, sizeof(commands_eq7) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } if (cmd_len > 7 && str[7] == '=') { cmd = upper_str; cmd[7] = 0; arg = str + 8; - - if (process_command_table(commands_eq8, - sizeof(commands_eq8) / sizeof(command_handler_t), - cmd, arg, output, mod)) { - } + process_command_table(commands_eq8, sizeof(commands_eq8) / sizeof(command_handler_t), cmd, arg, output, mod); + cmd_reached = 1; } - if (cmd_output != NULL) strcpy(cmd_output, output); + if (cmd_output != NULL && cmd_reached) strcpy(cmd_output, output); + if (cmd_reached) strcpy(cmd_output, "?\0"); } \ No newline at end of file diff --git a/src/lib.c b/src/lib.c index 2d23b7f..5e15230 100644 --- a/src/lib.c +++ b/src/lib.c @@ -32,16 +32,11 @@ uint16_t crc16_ccitt(char* data, uint16_t len) { uint16_t get_block_grom_group(RDSGroup *group, uint8_t block) { switch (block) { - case 0: - return group->a; - case 1: - return group->b; - case 2: - return group->c; - case 3: - return group->d; - default: - return 0; + case 0: return group->a; + case 1: return group->b; + case 2: return group->c; + case 3: return group->d; + default: return 0; } } @@ -59,9 +54,7 @@ void add_checkwords(RDSGroup *group, uint8_t *bits) for (uint8_t i = 0; i < GROUP_LENGTH; i++) { offset_word = offset_words[i]; - if (i == 2 && group->is_type_b) { - offset_word = offset_words[4]; - } + if (i == 2 && group->is_type_b) offset_word = offset_words[4]; uint16_t block = get_block_grom_group(group, i); @@ -107,9 +100,7 @@ uint8_t add_rds_af_oda(RDSAFsODA *af_list, float freq) { af_list->afs[af_list->num_entries + 0] = AF_CODE_LFMF_FOLLOWS; af_list->afs[af_list->num_entries + 1] = af; af_list->num_entries += 2; - } else { - return 1; - } + } else return 1; af_list->num_afs++; @@ -138,16 +129,14 @@ uint8_t add_rds_af(RDSAFs *af_list, float freq) { af_list->afs[af_list->num_entries + 0] = AF_CODE_LFMF_FOLLOWS; af_list->afs[af_list->num_entries + 1] = af; af_list->num_entries += 2; - } else { - return 1; - } + } else return 1; af_list->num_afs++; return 0; } -char *convert_to_rds_charset(char *str) { +char *convert_to_rdscharset(char *str) { static char new_str[255]; uint8_t i = 0; diff --git a/src/lib.h b/src/lib.h index a2bf4f6..93593d0 100644 --- a/src/lib.h +++ b/src/lib.h @@ -9,4 +9,4 @@ uint16_t get_block_grom_group(RDSGroup *group, uint8_t block); extern void add_checkwords(RDSGroup *group, uint8_t *bits); extern uint8_t add_rds_af_oda(RDSAFsODA *af_list, float freq); extern uint8_t add_rds_af(RDSAFs *af_list, float freq); -extern char *convert_to_rds_charset(char *str); \ No newline at end of file +extern char *convert_to_rdscharset(char *str); \ No newline at end of file diff --git a/src/modulator.c b/src/modulator.c index 3694773..964528e 100644 --- a/src/modulator.c +++ b/src/modulator.c @@ -3,53 +3,75 @@ static float waveform[2][FILTER_SIZE]; void Modulator_saveToFile(RDSModulatorParameters *emp, const char *option) { - char encoderPath[256]; - snprintf(encoderPath, sizeof(encoderPath), "%s/.rdsModulator", getenv("HOME")); + char modulatorPath[128]; + snprintf(modulatorPath, sizeof(modulatorPath), "%s/.rdsModulator", getenv("HOME")); FILE *file; - RDSModulatorParameters tempEncoder; - file = fopen(encoderPath, "rb"); + RDSModulatorParameters tempMod; + RDSModulatorParametersFile tempFile; + file = fopen(modulatorPath, "rb"); if (file != NULL) { - fread(&tempEncoder, sizeof(RDSModulatorParameters), 1, file); + fread(&tempFile, sizeof(RDSModulatorParametersFile), 1, file); fclose(file); } else { - memcpy(&tempEncoder, emp, sizeof(RDSModulatorParameters)); + memset(&tempFile, 0, sizeof(RDSModulatorParametersFile)); + tempFile.check = 160; + memcpy(&tempFile.params, emp, sizeof(RDSModulatorParameters)); + tempFile.crc = crc16_ccitt((char*)&tempFile, sizeof(RDSModulatorParametersFile) - sizeof(uint16_t)); } + memcpy(&tempMod, &tempFile.params, sizeof(RDSModulatorParameters)); if (strcmp(option, "LEVEL") == 0) { - tempEncoder.level = emp->level; + tempMod.level = emp->level; } else if (strcmp(option, "RDSGEN") == 0) { - tempEncoder.rdsgen = emp->rdsgen; + tempMod.rdsgen = emp->rdsgen; } else if (strcmp(option, "ALL") == 0) { - tempEncoder.level = emp->level; - tempEncoder.rdsgen = emp->rdsgen; + tempMod.level = emp->level; + tempMod.rdsgen = emp->rdsgen; } else { return; } + + memcpy(&tempFile.params, &tempMod, sizeof(RDSModulatorParameters)); + tempFile.check = 160; + tempFile.crc = crc16_ccitt((char*)&tempFile, sizeof(RDSModulatorParametersFile) - sizeof(uint16_t)); - file = fopen(encoderPath, "wb"); + file = fopen(modulatorPath, "wb"); if (file == NULL) { perror("Error opening file"); return; } - fwrite(&tempEncoder, sizeof(RDSModulatorParameters), 1, file); + fwrite(&tempFile, sizeof(RDSModulatorParameters), 1, file); fclose(file); } void Modulator_loadFromFile(RDSModulatorParameters *emp) { - char encoderPath[256]; - snprintf(encoderPath, sizeof(encoderPath), "%s/.rdsModulator", getenv("HOME")); - FILE *file = fopen(encoderPath, "rb"); + char modulatorPath[128]; + snprintf(modulatorPath, sizeof(modulatorPath), "%s/.rdsModulator", getenv("HOME")); + FILE *file = fopen(modulatorPath, "rb"); if (file == NULL) { perror("Error opening file"); return; } - fread(emp, sizeof(RDSModulatorParameters), 1, file); + RDSModulatorParametersFile tempFile; + fread(&tempFile, sizeof(RDSModulatorParametersFile), 1, file); + if (tempFile.check != 160) { + fprintf(stderr, "[RDSMODULATOR-FILE] Invalid file format\n"); + fclose(file); + return; + } + uint16_t calculated_crc = crc16_ccitt((char*)&tempFile, sizeof(RDSModulatorParametersFile) - sizeof(uint16_t)); + if (calculated_crc != tempFile.crc) { + fprintf(stderr, "[RDSMODULATOR-FILE] CRC mismatch! Data may be corrupted\n"); + fclose(file); + return; + } + memcpy(emp, &tempFile.params, sizeof(RDSModulatorParameters)); fclose(file); } int modulatorsaved() { - char encoderPath[256]; + char encoderPath[128]; snprintf(encoderPath, sizeof(encoderPath), "%s/.rdsModulator", getenv("HOME")); FILE *file = fopen(encoderPath, "rb"); if (file) { @@ -121,15 +143,6 @@ float get_rds_sample(RDSModulator* rdsMod, uint8_t stream) { rdsMod->data[stream].sample_buffer[rdsMod->data[stream].out_sample_index++] = 0; if (rdsMod->data[stream].out_sample_index == SAMPLE_BUFFER_SIZE) rdsMod->data[stream].out_sample_index = 0; - uint8_t tooutput = 1; - if (rdsMod->params.rdsgen == 0) { - tooutput = 0; - } else { - if(rdsMod->params.rdsgen == 1) { - if (stream == 1) { - tooutput = 0; - } - } - } + uint8_t tooutput = rdsMod->params.rdsgen > stream ? 1 : 0; return sample*rdsMod->params.level*tooutput; } diff --git a/src/modulator.h b/src/modulator.h index 246f1fe..e6a514f 100644 --- a/src/modulator.h +++ b/src/modulator.h @@ -9,6 +9,13 @@ typedef struct uint8_t rdsgen : 2; } RDSModulatorParameters; +typedef struct +{ + uint8_t check; + RDSModulatorParameters params; + uint16_t crc; +} RDSModulatorParametersFile; + typedef struct { uint8_t symbol_shift: 7; diff --git a/src/rds.c b/src/rds.c index 0b49aac..ba78283 100644 --- a/src/rds.c +++ b/src/rds.c @@ -5,7 +5,7 @@ #include void saveToFile(RDSEncoder *emp, const char *option) { - char encoderPath[256]; + char encoderPath[128]; snprintf(encoderPath, sizeof(encoderPath), "%s/.rdsEncoder", getenv("HOME")); FILE *file; @@ -53,7 +53,7 @@ void saveToFile(RDSEncoder *emp, const char *option) { void loadFromFile(RDSEncoder *enc) { RDSEncoderFile rdsEncoderfile; - char encoderPath[256]; + char encoderPath[128]; snprintf(encoderPath, sizeof(encoderPath), "%s/.rdsEncoder", getenv("HOME")); FILE *file = fopen(encoderPath, "rb"); if (file == NULL) { @@ -69,7 +69,6 @@ void loadFromFile(RDSEncoder *enc) { } uint16_t calculated_crc = crc16_ccitt((char*)&rdsEncoderfile, sizeof(RDSEncoderFile) - sizeof(uint16_t)); - if (calculated_crc != rdsEncoderfile.crc) { fprintf(stderr, "[RDSENCODER-FILE] CRC mismatch! Data may be corrupted\n"); return; @@ -84,7 +83,7 @@ void loadFromFile(RDSEncoder *enc) { } int rdssaved() { - char encoderPath[256]; + char encoderPath[128]; snprintf(encoderPath, sizeof(encoderPath), "%s/.rdsEncoder", getenv("HOME")); FILE *file = fopen(encoderPath, "rb"); if (file) { @@ -99,40 +98,32 @@ static uint16_t get_next_af(RDSEncoder* enc) { if (enc->data[enc->program].af.num_afs) { if (enc->state[enc->program].af_state == 0) { - out = (AF_CODE_NUM_AFS_BASE + enc->data[enc->program].af.num_afs) << 8; - out |= enc->data[enc->program].af.afs[0]; - enc->state[enc->program].af_state += 1; + out = (AF_CODE_NUM_AFS_BASE + enc->data[enc->program].af.num_afs) << 8 | enc->data[enc->program].af.afs[0]; + enc->state[enc->program].af_state++; } else { out = enc->data[enc->program].af.afs[enc->state[enc->program].af_state] << 8; - if (enc->data[enc->program].af.afs[enc->state[enc->program].af_state + 1]) { - out |= enc->data[enc->program].af.afs[enc->state[enc->program].af_state + 1]; - } else { + if (enc->data[enc->program].af.afs[enc->state[enc->program].af_state + 1]) out |= enc->data[enc->program].af.afs[enc->state[enc->program].af_state + 1]; + else { out |= AF_CODE_FILLER; enc->state[enc->program].af_state += 2; } } if (enc->state[enc->program].af_state >= enc->data[enc->program].af.num_entries) enc->state[enc->program].af_state = 0; - } else { - out = AF_CODE_NUM_AFS_BASE << 8 | AF_CODE_FILLER; - } + } else out = AF_CODE_NUM_AFS_BASE << 8 | AF_CODE_FILLER; return out; } static void get_next_af_oda(RDSEncoder* enc, uint16_t* af_group) { uint8_t offset = 0; - if (enc->state[enc->program].af_oda_state == 0) { - af_group[0] = (AF_CODE_NUM_AFS_BASE + enc->data[enc->program].af_oda.num_afs); - } else { + if (enc->state[enc->program].af_oda_state == 0) af_group[0] = (AF_CODE_NUM_AFS_BASE + enc->data[enc->program].af_oda.num_afs); + else { af_group[0] = enc->data[enc->program].af_oda.afs[enc->state[enc->program].af_oda_state++]; offset++; } for(int i = 0; i < 3; i++) { - if (enc->data[enc->program].af_oda.afs[enc->state[enc->program].af_oda_state + offset]) { - af_group[i + 1] = enc->data[enc->program].af_oda.afs[enc->state[enc->program].af_oda_state + offset]; - } else { - af_group[i + 1] = AF_CODE_FILLER; - } + if (enc->data[enc->program].af_oda.afs[enc->state[enc->program].af_oda_state + offset]) af_group[i + 1] = enc->data[enc->program].af_oda.afs[enc->state[enc->program].af_oda_state + offset]; + else af_group[i + 1] = AF_CODE_FILLER; enc->state[enc->program].af_oda_state++; } if (enc->state[enc->program].af_oda_state >= enc->data[enc->program].af_oda.num_entries) enc->state[enc->program].af_oda_state = 0; @@ -143,28 +134,22 @@ static uint16_t get_next_af_eon(RDSEncoder* enc, uint8_t eon_index) { if (enc->data[enc->program].eon[eon_index].af.num_afs) { if (enc->state[enc->program].eon_states[eon_index].af_state == 0) { - out = (AF_CODE_NUM_AFS_BASE + enc->data[enc->program].af.num_afs) << 8; - out |= enc->data[enc->program].eon[eon_index].af.afs[0]; + out = (AF_CODE_NUM_AFS_BASE + enc->data[enc->program].af.num_afs) << 8 | enc->data[enc->program].eon[eon_index].af.afs[0]; enc->state[enc->program].eon_states[eon_index].af_state += 1; } else { out = enc->data[enc->program].eon[eon_index].af.afs[enc->state[enc->program].eon_states[eon_index].af_state] << 8; - if (enc->data[enc->program].eon[eon_index].af.afs[enc->state[enc->program].eon_states[eon_index].af_state + 1]) { - out |= enc->data[enc->program].eon[eon_index].af.afs[enc->state[enc->program].eon_states[eon_index].af_state + 1]; - } else { + if (enc->data[enc->program].eon[eon_index].af.afs[enc->state[enc->program].eon_states[eon_index].af_state + 1]) out |= enc->data[enc->program].eon[eon_index].af.afs[enc->state[enc->program].eon_states[eon_index].af_state + 1]; + else { out |= AF_CODE_FILLER; enc->state[enc->program].eon_states[eon_index].af_state += 2; } } if (enc->state[enc->program].eon_states[eon_index].af_state >= enc->data[enc->program].eon[eon_index].af.num_entries) enc->state[enc->program].eon_states[eon_index].af_state = 0; - } else { - out = AF_CODE_NUM_AFS_BASE << 8 | AF_CODE_FILLER; - } + } else out = AF_CODE_NUM_AFS_BASE << 8 | AF_CODE_FILLER; return out; } -// #endregion -// #region Group encoding static void get_rds_ps_group(RDSEncoder* enc, RDSGroup *group) { if(enc->state[enc->program].ps_csegment == 0) { if(enc->state[enc->program].ps_update) { @@ -194,35 +179,33 @@ static void get_rds_ps_group(RDSEncoder* enc, RDSGroup *group) { static void get_rds_fasttuning_group(RDSEncoder* enc, RDSGroup *group) { group->b |= 15 << 12; + group->b |= 1 << 11; + group->is_type_b = 1; group->b |= enc->data[enc->program].ta << 4; if(enc->state[enc->program].fasttuning_state == 0) group->b |= enc->data[enc->program].dpty << 2; group->b |= enc->state[enc->program].fasttuning_state; - - // are blocks b and d the same or not? group->d = group->b; enc->state[enc->program].fasttuning_state++; if (enc->state[enc->program].fasttuning_state == 4) enc->state[enc->program].fasttuning_state = 0; - - group->is_type_b = 1; } static void get_rds_rt_group(RDSEncoder* enc, RDSGroup *group) { - if (enc->state[enc->program].rt_update && enc->data[enc->program].rt1_enabled && !enc->state[enc->program].current_rt) { + if (enc->state[enc->program].rt_update && enc->data[enc->program].rt1_enabled && !enc->data[enc->program].current_rt) { memcpy(enc->state[enc->program].rt_text, enc->data[enc->program].rt1, RT_LENGTH); enc->state[enc->program].rt_ab ^= 1; enc->state[enc->program].rt_update = 0; enc->state[enc->program].rt_state = 0; - enc->state[enc->program].current_rt = 0; + enc->data[enc->program].current_rt = 0; } - if(enc->state[enc->program].rt2_update && enc->data[enc->program].rt2_enabled && enc->state[enc->program].current_rt) { + if(enc->state[enc->program].rt2_update && enc->data[enc->program].rt2_enabled && enc->data[enc->program].current_rt) { memcpy(enc->state[enc->program].rt_text, enc->data[enc->program].rt2, RT_LENGTH); enc->state[enc->program].rt_ab ^= 1; enc->state[enc->program].rt2_update = 0; enc->state[enc->program].rt_state = 0; - enc->state[enc->program].current_rt = 1; + enc->data[enc->program].current_rt = 1; } uint8_t ab = enc->state[enc->program].rt_ab; @@ -232,9 +215,8 @@ static void get_rds_rt_group(RDSEncoder* enc, RDSGroup *group) { ab = 0; break; case 1: - ab = (enc->state[enc->program].current_rt == 0) ? 0 : 1; + ab = (enc->data[enc->program].current_rt == 0) ? 0 : 1; break; - case 2: default: break; } @@ -247,14 +229,13 @@ static void get_rds_rt_group(RDSEncoder* enc, RDSGroup *group) { group->d = enc->state[enc->program].rt_text[enc->state[enc->program].rt_state * 4 + 2] << 8; group->d |= enc->state[enc->program].rt_text[enc->state[enc->program].rt_state * 4 + 3]; - uint8_t segments = (enc->state[enc->program].current_rt == 1) ? enc->state[enc->program].rt2_segments : enc->state[enc->program].rt_segments; + uint8_t segments = (enc->data[enc->program].current_rt == 1) ? enc->state[enc->program].rt2_segments : enc->state[enc->program].rt_segments; enc->state[enc->program].rt_state++; if (enc->state[enc->program].rt_state == segments) enc->state[enc->program].rt_state = 0; } static void get_rds_rtp_oda_group(RDSEncoder* enc, RDSGroup *group) { (void)enc; group->b |= 3 << 12; - group->b |= 11 << 1; group->d = ODA_AID_RTPLUS; } @@ -338,7 +319,7 @@ static void get_rds_ptyn_group(RDSEncoder* enc, RDSGroup *group) { group->b |= 10 << 12 | enc->state[enc->program].ptyn_state; group->b |= enc->state[enc->program].ptyn_ab << 4; - group->c = enc->state[enc->program].ptyn_text[enc->state[enc->program].ptyn_state * 4 + 0] << 8; + group->c = enc->state[enc->program].ptyn_text[enc->state[enc->program].ptyn_state * 4] << 8; group->c |= enc->state[enc->program].ptyn_text[enc->state[enc->program].ptyn_state * 4 + 1]; group->d = enc->state[enc->program].ptyn_text[enc->state[enc->program].ptyn_state * 4 + 2] << 8; group->d |= enc->state[enc->program].ptyn_text[enc->state[enc->program].ptyn_state * 4 + 3]; @@ -354,7 +335,7 @@ static void get_rds_lps_group(RDSEncoder* enc, RDSGroup *group) { } group->b |= 15 << 12 | enc->state[enc->program].lps_state; - group->c = enc->state[enc->program].lps_text[enc->state[enc->program].lps_state * 4 ] << 8; + group->c = enc->state[enc->program].lps_text[enc->state[enc->program].lps_state * 4] << 8; group->c |= enc->state[enc->program].lps_text[enc->state[enc->program].lps_state * 4 + 1]; group->d = enc->state[enc->program].lps_text[enc->state[enc->program].lps_state * 4 + 2] << 8; group->d |= enc->state[enc->program].lps_text[enc->state[enc->program].lps_state * 4 + 3]; @@ -408,54 +389,56 @@ static void get_rds_ertplus_group(RDSEncoder* enc, RDSGroup *group) { static void get_rds_eon_group(RDSEncoder* enc, RDSGroup *group) { RDSEON eon; -get_eon: eon = enc->data[enc->program].eon[enc->state[enc->program].eon_index]; - group->b |= 14 << 12; - group->b |= eon.tp << 4; + while(1) { + group->b |= 14 << 12; + group->b |= eon.tp << 4; - switch (enc->state[enc->program].eon_state) - { - case 0: - case 1: - case 2: - case 3: - group->c = eon.ps[enc->state[enc->program].eon_state*2] << 8; - group->c |= eon.ps[enc->state[enc->program].eon_state*2 + 1]; - group->b |= enc->state[enc->program].eon_state; - break; - case 4: - group->c = get_next_af_eon(enc, enc->state[enc->program].eon_index); - group->b |= enc->state[enc->program].eon_state; - break; - case 5: // 13 - group->c = eon.pty << 11; - if(eon.tp) group->c |= eon.ta; - group->b |= 13; - break; - case 6: // 15 - group->c = eon.data; - group->b |= 15; - break; - } - - group->d = eon.pi; - - if(enc->state[enc->program].eon_state == 6) { - enc->state[enc->program].eon_index++; - - uint8_t i = 0; - while(i < 4 && !enc->data[enc->program].eon[enc->state[enc->program].eon_index].enabled) { - enc->state[enc->program].eon_index++; - if(enc->state[enc->program].eon_index >= 4) { - enc->state[enc->program].eon_index = 0; - } - i++; + switch (enc->state[enc->program].eon_state) + { + case 0: + case 1: + case 2: + case 3: + group->c = eon.ps[enc->state[enc->program].eon_state*2] << 8; + group->c |= eon.ps[enc->state[enc->program].eon_state*2+1]; + group->b |= enc->state[enc->program].eon_state; + break; + case 4: + group->c = get_next_af_eon(enc, enc->state[enc->program].eon_index); + group->b |= enc->state[enc->program].eon_state; + break; + case 5: // 13 + group->c = eon.pty << 11; + if(eon.tp) group->c |= eon.ta; + group->b |= 13; + break; + case 6: // 15 + group->c = eon.data; + group->b |= 15; + break; } - enc->state[enc->program].eon_state = 0; - goto get_eon; - } else { - enc->state[enc->program].eon_state++; + group->d = eon.pi; + + if(enc->state[enc->program].eon_state == 6) { + enc->state[enc->program].eon_index++; + + uint8_t i = 0; + while(i < 4 && !enc->data[enc->program].eon[enc->state[enc->program].eon_index].enabled) { + enc->state[enc->program].eon_index++; + if(enc->state[enc->program].eon_index == 4) { + enc->state[enc->program].eon_index = 0; + } + eon = enc->data[enc->program].eon[enc->state[enc->program].eon_index]; + i++; + } + + enc->state[enc->program].eon_state = 0; + } else { + enc->state[enc->program].eon_state++; + break; + } } } @@ -466,15 +449,14 @@ static void get_rds_ert_group(RDSEncoder* enc, RDSGroup *group) { } group->b |= 12 << 12 | (enc->state[enc->program].ert_state & 31); - group->c = enc->state[enc->program].ert_text[enc->state[enc->program].ert_state * 4 ] << 8; + group->c = enc->state[enc->program].ert_text[enc->state[enc->program].ert_state * 4] << 8; group->c |= enc->state[enc->program].ert_text[enc->state[enc->program].ert_state * 4 + 1]; - group->d = enc->state[enc->program].ert_text[enc->state[enc->program].ert_state * 4 + 2] << 8; + group->d = enc->state[enc->program].ert_text[enc->state[enc->program].ert_state * 4 + 2] << 8; group->d |= enc->state[enc->program].ert_text[enc->state[enc->program].ert_state * 4 + 3]; enc->state[enc->program].ert_state++; if (enc->state[enc->program].ert_state == enc->state[enc->program].ert_segments) enc->state[enc->program].ert_state = 0; } -// #endregion static uint8_t get_rds_custom_groups(RDSEncoder* enc, RDSGroup *group) { if(enc->state[enc->program].custom_group[0] == 1) { @@ -503,24 +485,21 @@ static uint8_t get_rds_custom_groups2(RDSEncoder* enc, RDSGroup *group) { static void get_rds_sequence_group(RDSEncoder* enc, RDSGroup *group, char* grp, uint8_t stream) { uint8_t udg_idx; - uint8_t idx_seq = (stream == 0) ? 1 : 3; - uint8_t idx2_seq = (stream == 0) ? 0 : 2; + uint8_t ps_seq_idx = (stream == 0) ? 1 : 3; + uint8_t grp_seq_idx = (stream == 0) ? 0 : 2; switch (*grp) { default: case '0': - if(enc->state[enc->program].grp_seq_idx[idx_seq] < 4) enc->state[enc->program].grp_seq_idx[idx2_seq]--; - else enc->state[enc->program].grp_seq_idx[idx_seq] = 0; + if(enc->state[enc->program].grp_seq_idx[ps_seq_idx] < 4) enc->state[enc->program].grp_seq_idx[grp_seq_idx]--; + else enc->state[enc->program].grp_seq_idx[ps_seq_idx] = 0; - enc->state[enc->program].grp_seq_idx[idx_seq]++; + enc->state[enc->program].grp_seq_idx[ps_seq_idx]++; get_rds_ps_group(enc, group); goto group_coded; case '1': - if(enc->state[enc->program].data_ecc == 0 && enc->data[enc->program].slc_data != 0) { - get_rds_slcdata_group(enc, group); - } else { - get_rds_ecc_group(enc, group); - } + if(enc->state[enc->program].data_ecc == 0 && enc->data[enc->program].slc_data != 0) get_rds_slcdata_group(enc, group); + else get_rds_ecc_group(enc, group); enc->state[enc->program].data_ecc ^= 1; goto group_coded; case '2': @@ -539,6 +518,7 @@ static void get_rds_sequence_group(RDSEncoder* enc, RDSGroup *group, char* grp, group->d = enc->data[enc->program].udg1[udg_idx][2]; enc->state[enc->program].udg_idxs[0]++; if(enc->state[enc->program].udg_idxs[0] == enc->data[enc->program].udg1_len) enc->state[enc->program].udg_idxs[0] = 0; + group->is_type_b = (group->a == 0 && IS_TYPE_B(group->b)); goto group_coded; case 'Y': udg_idx = enc->state[enc->program].udg_idxs[1]; @@ -547,33 +527,24 @@ static void get_rds_sequence_group(RDSEncoder* enc, RDSGroup *group, char* grp, group->d = enc->data[enc->program].udg2[udg_idx][2]; enc->state[enc->program].udg_idxs[1]++; if(enc->state[enc->program].udg_idxs[1] == enc->data[enc->program].udg2_len) enc->state[enc->program].udg_idxs[1] = 0; + group->is_type_b = (group->a == 0 && IS_TYPE_B(group->b)); goto group_coded; case 'R': - if(enc->state[enc->program].rtp_oda == 0) { - get_rds_rtplus_group(enc, group); - } else { - get_rds_rtp_oda_group(enc, group); - } + if(enc->state[enc->program].rtp_oda == 0) get_rds_rtplus_group(enc, group); + else get_rds_rtp_oda_group(enc, group); enc->state[enc->program].rtp_oda ^= 1; goto group_coded; case 'P': - if(enc->state[enc->program].ert_oda == 0) { - get_rds_ertplus_group(enc, group); - } else { - get_rds_ertp_oda_group(enc, group); - } + if(enc->state[enc->program].ert_oda == 0) get_rds_ertplus_group(enc, group); + else get_rds_ertp_oda_group(enc, group); + enc->state[enc->program].ert_oda ^= 1; goto group_coded; case 'S': - if(enc->state[enc->program].ert_oda == 0) { - get_rds_ert_group(enc, group); - } else { - get_rds_ert_oda_group(enc, group); - } + if(enc->state[enc->program].ert_oda == 0) get_rds_ert_group(enc, group); + else get_rds_ert_oda_group(enc, group); enc->state[enc->program].ert_oda ^= 1; goto group_coded; - // TODO: add uecp - // TODO: readd ODA case 'F': get_rds_lps_group(enc, group); goto group_coded; @@ -581,11 +552,8 @@ static void get_rds_sequence_group(RDSEncoder* enc, RDSGroup *group, char* grp, get_rds_fasttuning_group(enc, group); goto group_coded; case 'U': - if(enc->state[enc->program].af_oda == 0) { - get_oda_af_group(enc, group); - } else { - get_oda_af_oda_group(enc, group); - } + if(enc->state[enc->program].af_oda == 0) get_oda_af_group(enc, group); + else get_oda_af_oda_group(enc, group); enc->state[enc->program].af_oda ^= 1; goto group_coded; } @@ -643,27 +611,27 @@ static void get_rds_group(RDSEncoder* enc, RDSGroup *group, uint8_t stream) { enc->state[enc->program].ta_timeout--; if(enc->state[enc->program].ta_timeout == 0) { enc->data[enc->program].ta = 0; - enc->state[enc->program].ta_timeout = enc->state[enc->program].original_ta_timeout; + enc->state[enc->program].ta_timeout_state = enc->state[enc->program].ta_timeout; }; } - if(enc->data[enc->program].rt1_enabled && enc->data[enc->program].rt2_enabled && enc->data[enc->program].rt_switching_period != 0) { - enc->data[enc->program].rt_switching_period--; - if(enc->data[enc->program].rt_switching_period == 0) { - enc->state[enc->program].current_rt ^= 1; - if (enc->state[enc->program].current_rt == 1) { + if(enc->data[enc->program].rt1_enabled && enc->data[enc->program].rt2_enabled && enc->state[enc->program].rt_switching_period_state) { + enc->state[enc->program].rt_switching_period_state--; + if(enc->state[enc->program].rt_switching_period_state == 0) { + enc->data[enc->program].current_rt ^= 1; + if (enc->data[enc->program].current_rt == 1) { memcpy(enc->state[enc->program].rt_text, enc->data[enc->program].rt2, RT_LENGTH); } else { memcpy(enc->state[enc->program].rt_text, enc->data[enc->program].rt1, RT_LENGTH); } enc->state[enc->program].rt_state = 0; - enc->data[enc->program].rt_switching_period = enc->data[enc->program].orignal_rt_switching_period; + enc->state[enc->program].rt_switching_period_state = enc->data[enc->program].rt_switching_period; } } - if(enc->data[enc->program].rt1_enabled && enc->data[enc->program].rt_text_timeout != 0) { - enc->data[enc->program].rt_text_timeout--; - if(enc->data[enc->program].rt_text_timeout == 0) { + if(enc->data[enc->program].rt1_enabled && enc->data[enc->program].current_rt == 0 && enc->state[enc->program].rt_text_timeout) { + enc->state[enc->program].rt_text_timeout_state--; + if(enc->state[enc->program].rt_text_timeout_state == 0) { enc->state[enc->program].rt_update = 1; memcpy(enc->state[enc->program].rt_text, enc->data[enc->program].default_rt, RT_LENGTH); } @@ -682,15 +650,15 @@ static void get_rds_group(RDSEncoder* enc, RDSGroup *group, uint8_t stream) { if(stream != 0) { group->a = 0; - if(get_rds_custom_groups2(enc, group)) { - goto group_coded_rds2; - } - if(enc->encoder_data.rds2_mode == 0) { // tunneling + if(get_rds_custom_groups2(enc, group)) goto group_coded_rds2; + + if(enc->encoder_data.rds2_mode == 0) { group->b = enc->state[enc->program].last_stream0_group[0]; group->c = enc->state[enc->program].last_stream0_group[1]; group->d = enc->state[enc->program].last_stream0_group[2]; + group->is_type_b = (group->a == 0 && IS_TYPE_B(group->b)); goto group_coded_rds2; - } else if(enc->encoder_data.rds2_mode == 1) { // independent tunneling + } else if(enc->encoder_data.rds2_mode == 1) { while(good_group == 0) { grp_sqc_idx = enc->state[enc->program].grp_seq_idx[2]; if(enc->data[enc->program].grp_sqc_rds2[grp_sqc_idx] == '\0') { @@ -718,9 +686,7 @@ static void get_rds_group(RDSEncoder* enc, RDSGroup *group, uint8_t stream) { } } - if(get_rds_custom_groups(enc, group)) { - goto group_coded; - } + if(get_rds_custom_groups(enc, group)) goto group_coded; while(good_group == 0) { grp_sqc_idx = enc->state[enc->program].grp_seq_idx[0]; @@ -750,15 +716,11 @@ group_coded_rds2: if(group->is_type_b) group->c = enc->data[enc->program].pi; group->b |= enc->data[enc->program].tp << 10; group->b |= enc->data[enc->program].pty << 5; - } else if(stream == 0) { - goto group_coded; - } + } else if(stream == 0) goto group_coded; return; group_coded: - if(stream != 0) { - goto group_coded_rds2; - } + if(stream != 0) goto group_coded_rds2; group->b |= enc->data[enc->program].tp << 10; group->b |= enc->data[enc->program].pty << 5; if(group->is_type_b) group->c = enc->data[enc->program].pi; @@ -799,9 +761,7 @@ void reset_rds_state(RDSEncoder* enc, uint8_t program) { utc = gmtime(&now); tempCoder.state[program].last_minute = utc->tm_min; - for(int i = 0; i < 4; i++) { - tempCoder.data[program].eon[i].ta = 0; - } + for(int i = 0; i < 4; i++) tempCoder.data[program].eon[i].ta = 0; memcpy(&(enc->state[program]), &(tempCoder.state[program]), sizeof(RDSState)); memcpy(&(enc->rtpState[program]), &(tempCoder.rtpState[program]), sizeof(RDSRTPlusState)); @@ -851,29 +811,23 @@ void init_rds_encoder(RDSEncoder* enc) { void set_rds_rt1(RDSEncoder* enc, char *rt1) { uint8_t i = 0, len = 0; - enc->data[enc->program].rt_text_timeout = enc->data[enc->program].original_rt_text_timeout; + enc->state[enc->program].rt_text_timeout_state = enc->data[enc->program].rt_text_timeout; enc->state[enc->program].rt_update = 1; memset(enc->data[enc->program].rt1, ' ', RT_LENGTH); while (*rt1 != 0 && len < RT_LENGTH) enc->data[enc->program].rt1[len++] = *rt1++; - while (len > 0 && enc->data[enc->program].rt1[len - 1] == ' ') { - len--; - } + while (len > 0 && enc->data[enc->program].rt1[len - 1] == ' ') len--; if (len < RT_LENGTH) { enc->state[enc->program].rt_segments = 0; - enc->data[enc->program].rt1[len++] = '\r'; - while (i < len) { i += 4; enc->state[enc->program].rt_segments++; } - } else { - enc->state[enc->program].rt_segments = 16; - } + } else enc->state[enc->program].rt_segments = 16; } void set_rds_rt2(RDSEncoder* enc, char *rt2) { @@ -884,22 +838,16 @@ void set_rds_rt2(RDSEncoder* enc, char *rt2) { memset(enc->data[enc->program].rt2, ' ', RT_LENGTH); while (*rt2 != 0 && len < RT_LENGTH) enc->data[enc->program].rt2[len++] = *rt2++; - while (len > 0 && enc->data[enc->program].rt2[len - 1] == ' ') { - len--; - } + while (len > 0 && enc->data[enc->program].rt2[len - 1] == ' ') len--; if (len < RT_LENGTH) { enc->state[enc->program].rt2_segments = 0; - enc->data[enc->program].rt2[len++] = '\r'; - while (i < len) { i += 4; enc->state[enc->program].rt2_segments++; } - } else { - enc->state[enc->program].rt2_segments = 16; - } + } else enc->state[enc->program].rt2_segments = 16; } void set_rds_ps(RDSEncoder* enc, char *ps) { @@ -936,14 +884,11 @@ void set_rds_lps(RDSEncoder* enc, char *lps) { if (len < LPS_LENGTH) { enc->state[enc->program].lps_segments = 0; - while (i < len) { i += 4; enc->state[enc->program].lps_segments++; } - } else { - enc->state[enc->program].lps_segments = 8; - } + } else enc->state[enc->program].lps_segments = 8; } void set_rds_ert(RDSEncoder* enc, char *ert) { @@ -951,44 +896,38 @@ void set_rds_ert(RDSEncoder* enc, char *ert) { enc->state[enc->program].ert_update = 1; - memset(enc->data[enc->program].ert, ' ', RT_LENGTH); - while (*ert != 0 && len < RT_LENGTH) enc->data[enc->program].ert[len++] = *ert++; + memset(enc->data[enc->program].ert, ' ', ERT_LENGTH); + while (*ert != 0 && len < ERT_LENGTH) enc->data[enc->program].ert[len++] = *ert++; - while (len > 0 && enc->data[enc->program].ert[len - 1] == ' ') { - len--; - } + while (len > 0 && enc->data[enc->program].ert[len - 1] == ' ') len--; - if (len < RT_LENGTH) { + if (len < ERT_LENGTH) { enc->state[enc->program].ert_segments = 0; - enc->data[enc->program].ert[len++] = '\r'; - while (i < len) { i += 4; enc->state[enc->program].ert_segments++; } - } else { - enc->state[enc->program].ert_segments = 32; - } + } else enc->state[enc->program].ert_segments = 32; } void set_rds_rtplus_flags(RDSEncoder* enc, uint8_t flags) { enc->rtpData[enc->program][0].enabled = (flags==2); - enc->rtpData[enc->program][0].running = flags & 1; + enc->rtpData[enc->program][0].running = flags & 1; } void set_rds_ertplus_flags(RDSEncoder* enc, uint8_t flags) { enc->rtpData[enc->program][1].enabled = (flags==2); - enc->rtpData[enc->program][1].running = flags & 1; + enc->rtpData[enc->program][1].running = flags & 1; } void set_rds_rtplus_tags(RDSEncoder* enc, uint8_t *tags) { - enc->rtpData[enc->program][0].type[0] = tags[0] & 0x3f; - enc->rtpData[enc->program][0].start[0] = tags[1] & 0x3f; - enc->rtpData[enc->program][0].len[0] = tags[2] & 0x3f; - enc->rtpData[enc->program][0].type[1] = tags[3] & 0x3f; - enc->rtpData[enc->program][0].start[1] = tags[4] & 0x3f; - enc->rtpData[enc->program][0].len[1] = tags[5] & 0x1f; + enc->rtpData[enc->program][0].type[0] = tags[0] & 0x3f; + enc->rtpData[enc->program][0].start[0] = tags[1] & 0x3f; + enc->rtpData[enc->program][0].len[0] = tags[2] & 0x3f; + enc->rtpData[enc->program][0].type[1] = tags[3] & 0x3f; + enc->rtpData[enc->program][0].start[1] = tags[4] & 0x3f; + enc->rtpData[enc->program][0].len[1] = tags[5] & 0x1f; enc->rtpState[enc->program][0].toggle ^= 1; enc->rtpData[enc->program][0].running = 1; @@ -996,12 +935,12 @@ void set_rds_rtplus_tags(RDSEncoder* enc, uint8_t *tags) { } void set_rds_ertplus_tags(RDSEncoder* enc, uint8_t *tags) { - enc->rtpData[enc->program][1].type[0] = tags[0] & 0x3f; - enc->rtpData[enc->program][1].start[0] = tags[1] & 0x3f; - enc->rtpData[enc->program][1].len[0] = tags[2] & 0x3f; - enc->rtpData[enc->program][1].type[1] = tags[3] & 0x3f; - enc->rtpData[enc->program][1].start[1] = tags[4] & 0x3f; - enc->rtpData[enc->program][1].len[1] = tags[5] & 0x1f; + enc->rtpData[enc->program][1].type[0] = tags[0] & 0x3f; + enc->rtpData[enc->program][1].start[0] = tags[1] & 0x3f; + enc->rtpData[enc->program][1].len[0] = tags[2] & 0x3f; + enc->rtpData[enc->program][1].type[1] = tags[3] & 0x3f; + enc->rtpData[enc->program][1].start[1] = tags[4] & 0x3f; + enc->rtpData[enc->program][1].len[1] = tags[5] & 0x1f; enc->rtpState[enc->program][1].toggle ^= 1; enc->rtpData[enc->program][1].running = 1; diff --git a/src/rds.h b/src/rds.h index a02d522..6850179 100644 --- a/src/rds.h +++ b/src/rds.h @@ -77,9 +77,8 @@ typedef struct { uint8_t rt2_enabled : 1; uint8_t rt_type : 2; uint8_t rt_text_timeout; - uint8_t original_rt_text_timeout; uint8_t rt_switching_period; - uint8_t orignal_rt_switching_period; + uint8_t current_rt : 1; char default_rt[RT_LENGTH]; char rt2[RT_LENGTH]; @@ -125,7 +124,6 @@ typedef struct { uint8_t rt_ab : 1; uint8_t rt_segments : 5; uint8_t rt2_segments : 5; - uint8_t current_rt : 1; char ert_text[ERT_LENGTH]; uint8_t ert_state : 6; @@ -145,6 +143,9 @@ typedef struct { uint16_t custom_group[GROUP_LENGTH]; uint16_t custom_group2[GROUP_LENGTH + 1]; + uint8_t rt_switching_period_state; + uint8_t rt_text_timeout_state; + uint8_t rtp_oda : 1; uint8_t ertp_oda : 1; uint8_t ert_oda : 1; @@ -156,8 +157,9 @@ typedef struct { uint8_t fasttuning_state : 3; uint8_t last_minute : 6; + uint8_t ta_timeout : 7; - uint8_t original_ta_timeout : 7; + uint8_t ta_timeout_state : 7; uint8_t eon_index : 3; uint8_t eon_state : 4;