diff --git a/src/freedv_api.c b/src/freedv_api.c index a158d2aa..d04dd7c8 100644 --- a/src/freedv_api.c +++ b/src/freedv_api.c @@ -247,7 +247,8 @@ void freedv_close(struct freedv *freedv) { FDV_MODE_ACTIVE(FREEDV_MODE_DATAC3, freedv->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC4, freedv->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC13, freedv->mode) || - FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, freedv->mode)) { + FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, freedv->mode) || + FDV_MODE_ACTIVE(FREEDV_MODE_DATA_CUSTOM, freedv->mode)) { FREE(freedv->rx_syms); FREE(freedv->rx_amps); FREE(freedv->ldpc); @@ -279,7 +280,8 @@ static int is_ofdm_mode(struct freedv *f) { FDV_MODE_ACTIVE(FREEDV_MODE_DATAC3, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC4, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC13, f->mode) || - FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode); + FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode) || + FDV_MODE_ACTIVE(FREEDV_MODE_DATA_CUSTOM, f->mode); } static int is_ofdm_data_mode(struct freedv *f) { @@ -288,7 +290,8 @@ static int is_ofdm_data_mode(struct freedv *f) { FDV_MODE_ACTIVE(FREEDV_MODE_DATAC3, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC4, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC13, f->mode) || - FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode); + FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode) || + FDV_MODE_ACTIVE(FREEDV_MODE_DATA_CUSTOM, f->mode); } /*---------------------------------------------------------------------------*\ @@ -479,7 +482,8 @@ void freedv_rawdatacomptx(struct freedv *f, COMP mod_out[], FDV_MODE_ACTIVE(FREEDV_MODE_DATAC3, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC4, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC13, f->mode) || - FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode)) + FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode) || + FDV_MODE_ACTIVE(FREEDV_MODE_DATA_CUSTOM, f->mode)) freedv_comptx_ofdm(f, mod_out); if (FDV_MODE_ACTIVE(FREEDV_MODE_FSK_LDPC, f->mode)) { @@ -1079,7 +1083,8 @@ int freedv_rawdatacomprx(struct freedv *f, unsigned char *packed_payload_bits, FDV_MODE_ACTIVE(FREEDV_MODE_DATAC3, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC4, f->mode) || FDV_MODE_ACTIVE(FREEDV_MODE_DATAC13, f->mode) || - FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode)) + FDV_MODE_ACTIVE(FREEDV_MODE_DATAC14, f->mode) || + FDV_MODE_ACTIVE(FREEDV_MODE_DATA_CUSTOM, f->mode)) rx_status = freedv_comp_short_rx_ofdm(f, (void *)demod_in, 0, 1.0f); if (FDV_MODE_ACTIVE(FREEDV_MODE_FSK_LDPC, f->mode)) { rx_status = freedv_rx_fsk_ldpc_data(f, demod_in); diff --git a/src/freedv_data_raw_rx.c b/src/freedv_data_raw_rx.c index 0353ae54..435648d7 100644 --- a/src/freedv_data_raw_rx.c +++ b/src/freedv_data_raw_rx.c @@ -39,6 +39,7 @@ #include "ldpc_codes.h" #include "modem_stats.h" #include "octave.h" +#include "ofdm_internal.h" /* other processes can end this program using signals */ @@ -216,6 +217,8 @@ int main(int argc, char *argv[]) { mode = FREEDV_MODE_DATAC13; if (!strcmp(argv[dx], "DATAC14") || !strcmp(argv[dx], "datac14")) mode = FREEDV_MODE_DATAC14; + if (!strcmp(argv[dx], "CUSTOM") || !strcmp(argv[dx], "custom")) + mode = FREEDV_MODE_DATA_CUSTOM; if (mode == -1) { fprintf(stderr, "Error in mode: %s\n", argv[dx]); exit(1); @@ -248,6 +251,23 @@ int main(int argc, char *argv[]) { fprintf(stderr, "Setting estimator limits to %d to %d Hz.\n", fsk_lower, fsk_upper); fsk_set_freq_est_limits(fsk, fsk_lower, fsk_upper); + } else if (mode == FREEDV_MODE_DATA_CUSTOM) { + // demonstrate custom OFDM raw data modes + struct OFDM_CONFIG ofdm_config; + ofdm_init_mode("datac14", &ofdm_config); + // modify datac14 to have 3 carriers instead of 4, which means + // we have to tweak Np, and the number of unique word bits + ofdm_config.nc = 3; + ofdm_config.np = 6; + ofdm_config.nuwbits = 48; + ofdm_config.bad_uw_errors = 18; + uint8_t uw[] = {1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 1, + 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0}; + memcpy(ofdm_config.tx_uw, uw, sizeof(uw)); + memcpy(&ofdm_config.tx_uw[ofdm_config.nuwbits - sizeof(uw)], uw, + sizeof(uw)); + adv.config = (void *)&ofdm_config; + freedv = freedv_open_advanced(mode, &adv); } else { freedv = freedv_open(mode); } @@ -264,8 +284,8 @@ int main(int argc, char *argv[]) { fsk->Ndft); } - /* for streaming bytes it's much easier use the modes that have a multiple of - * 8 payload bits/frame */ + /* for streaming bytes it's much easier use the modes that have a multiple + * of 8 payload bits/frame */ assert((freedv_get_bits_per_modem_frame(freedv) % 8) == 0); int bytes_per_modem_frame = freedv_get_bits_per_modem_frame(freedv) / 8; // last two bytes used for CRC diff --git a/src/freedv_data_raw_tx.c b/src/freedv_data_raw_tx.c index cb741077..ce5da562 100644 --- a/src/freedv_data_raw_tx.c +++ b/src/freedv_data_raw_tx.c @@ -238,6 +238,8 @@ int main(int argc, char *argv[]) { mode = FREEDV_MODE_DATAC13; if (!strcmp(argv[dx], "DATAC14") || !strcmp(argv[dx], "datac14")) mode = FREEDV_MODE_DATAC14; + if (!strcmp(argv[dx], "CUSTOM") || !strcmp(argv[dx], "custom")) + mode = FREEDV_MODE_DATA_CUSTOM; if (mode == -1) { fprintf(stderr, "Error: in mode: %s", argv[dx]); exit(1); @@ -259,10 +261,28 @@ int main(int argc, char *argv[]) { exit(1); } - if (mode != FREEDV_MODE_FSK_LDPC) - freedv = freedv_open(mode); - else + if (mode == FREEDV_MODE_FSK_LDPC) + freedv = freedv_open_advanced(mode, &adv); + else if (mode == FREEDV_MODE_DATA_CUSTOM) { + // demonstrate custom OFDM raw data modes + struct OFDM_CONFIG ofdm_config; + ofdm_init_mode("datac14", &ofdm_config); + // modify datac14 to have 3 carriers instead of 4, which means + // we have to tweak Np, and the number of unique word bits + ofdm_config.nc = 3; + ofdm_config.np = 6; + ofdm_config.nuwbits = 48; + ofdm_config.bad_uw_errors = 18; + uint8_t uw[] = {1, 1, 0, 0, 1, 0, 1, 0, 1, 1, 1, 1, + 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0}; + memcpy(ofdm_config.tx_uw, uw, sizeof(uw)); + memcpy(&ofdm_config.tx_uw[ofdm_config.nuwbits - sizeof(uw)], uw, + sizeof(uw)); + adv.config = (void *)&ofdm_config; freedv = freedv_open_advanced(mode, &adv); + } else { + freedv = freedv_open(mode); + } assert(freedv != NULL);