From c4d5c39ed53d9d6e547445aaa938d8f664f936f4 Mon Sep 17 00:00:00 2001 From: KubaPro010 Date: Sun, 27 Apr 2025 13:11:42 +0200 Subject: [PATCH] not sure --- .vscode/.server-controller-port.log | 2 +- .vscode/settings.json | 3 +- CMakeLists.txt | 10 ++- {lib => dsp}/bs412.c | 0 {lib => dsp}/bs412.h | 0 {lib => dsp}/constants.h | 0 {lib => dsp}/filters.c | 0 {lib => dsp}/filters.h | 2 +- {lib => dsp}/fm_modulator.c | 0 {lib => dsp}/fm_modulator.h | 0 {lib => dsp}/gain_control.c | 0 {lib => dsp}/gain_control.h | 0 {lib => dsp}/oscillator.c | 0 {lib => dsp}/oscillator.h | 0 src/chimer95.c | 31 +++----- src/dcf95.c | 118 +++++++++------------------- src/fm95.c | 65 ++++++--------- 17 files changed, 82 insertions(+), 149 deletions(-) rename {lib => dsp}/bs412.c (100%) rename {lib => dsp}/bs412.h (100%) rename {lib => dsp}/constants.h (100%) rename {lib => dsp}/filters.c (100%) rename {lib => dsp}/filters.h (92%) rename {lib => dsp}/fm_modulator.c (100%) rename {lib => dsp}/fm_modulator.h (100%) rename {lib => dsp}/gain_control.c (100%) rename {lib => dsp}/gain_control.h (100%) rename {lib => dsp}/oscillator.c (100%) rename {lib => dsp}/oscillator.h (100%) diff --git a/.vscode/.server-controller-port.log b/.vscode/.server-controller-port.log index aa53feb..559759d 100644 --- a/.vscode/.server-controller-port.log +++ b/.vscode/.server-controller-port.log @@ -1,5 +1,5 @@ { "port": 13452, - "time": 1744527962187, + "time": 1745750934180, "version": "0.0.3" } \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json index 3b46967..92b431d 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -23,7 +23,8 @@ "bs412.h": "c", "gain_control.h": "c", "optimization.h": "c", - "string.h": "c" + "string.h": "c", + "getopt.h": "c" }, "C_Cpp.errorSquiggles": "disabled" } \ No newline at end of file diff --git a/CMakeLists.txt b/CMakeLists.txt index ea94f1e..fc628f2 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -7,15 +7,19 @@ set(CMAKE_C_STANDARD_REQUIRED YES) file(GLOB SRC_FILES "src/*.c") -file(GLOB LIB_FILES "lib/*.c") +file(GLOB DSP_FILES "dsp/*.c") + +# file(GLOB LIB_FILES "lib/*.c") file(GLOB IO_FILES "io/*.c") -add_library(libfm OBJECT ${LIB_FILES}) +# add_library(libfm OBJECT ${LIB_FILES}) + +add_library(libfmdsp OBJECT ${DSP_FILES}) add_library(libfmio OBJECT ${IO_FILES}) -set(FM_LIBS libfm libfmio pulse pulse-simple m) +set(FM_LIBS libfmio libfmdsp pulse pulse-simple m) foreach(SRC_FILE ${SRC_FILES}) get_filename_component(EXEC_NAME ${SRC_FILE} NAME_WE) diff --git a/lib/bs412.c b/dsp/bs412.c similarity index 100% rename from lib/bs412.c rename to dsp/bs412.c diff --git a/lib/bs412.h b/dsp/bs412.h similarity index 100% rename from lib/bs412.h rename to dsp/bs412.h diff --git a/lib/constants.h b/dsp/constants.h similarity index 100% rename from lib/constants.h rename to dsp/constants.h diff --git a/lib/filters.c b/dsp/filters.c similarity index 100% rename from lib/filters.c rename to dsp/filters.c diff --git a/lib/filters.h b/dsp/filters.h similarity index 92% rename from lib/filters.h rename to dsp/filters.h index 76615c6..1c16e66 100644 --- a/lib/filters.h +++ b/dsp/filters.h @@ -4,7 +4,7 @@ #include #include #include "constants.h" -#include "optimization.h" +#include "../lib/optimization.h" #include "oscillator.h" typedef struct diff --git a/lib/fm_modulator.c b/dsp/fm_modulator.c similarity index 100% rename from lib/fm_modulator.c rename to dsp/fm_modulator.c diff --git a/lib/fm_modulator.h b/dsp/fm_modulator.h similarity index 100% rename from lib/fm_modulator.h rename to dsp/fm_modulator.h diff --git a/lib/gain_control.c b/dsp/gain_control.c similarity index 100% rename from lib/gain_control.c rename to dsp/gain_control.c diff --git a/lib/gain_control.h b/dsp/gain_control.h similarity index 100% rename from lib/gain_control.h rename to dsp/gain_control.h diff --git a/lib/oscillator.c b/dsp/oscillator.c similarity index 100% rename from lib/oscillator.c rename to dsp/oscillator.c diff --git a/lib/oscillator.h b/dsp/oscillator.h similarity index 100% rename from lib/oscillator.h rename to dsp/oscillator.h diff --git a/src/chimer95.c b/src/chimer95.c index 84649a7..17aadc2 100644 --- a/src/chimer95.c +++ b/src/chimer95.c @@ -9,8 +9,8 @@ #define buffer_tlength_fragsize 1024 #define buffer_prebuf 0 -#include "../lib/constants.h" -#include "../lib/oscillator.h" +#include "../dsp/constants.h" +#include "../dsp/oscillator.h" #include "../lib/optimization.h" #define DEFAULT_FREQ 1000.0f @@ -143,9 +143,7 @@ int check_time_for_sequence(int test_mode, int offset) { static int last_minute = -1; time_t now = time(NULL); - if (now == last_check) { - return SEQ_NONE; - } + if (now == last_check) return SEQ_NONE; last_check = now; struct tm *utc_time = gmtime(&now); @@ -229,12 +227,12 @@ int main(int argc, char **argv) { } printf("Configuration:\n"); - printf(" Output device: %s\n", audio_output_device); - printf(" Frequency: %.1f Hz\n", freq); - printf(" Sample rate: %d Hz\n", sample_rate); - printf(" Volume: %.2f\n", master_volume); - printf(" Time offset: %d seconds\n", offset); - printf(" Test mode: %s\n", test_mode ? "Enabled" : "Disabled"); + printf("\tOutput device: %s\n", audio_output_device); + printf("\tFrequency: %.1f Hz\n", freq); + printf("\tSample rate: %d Hz\n", sample_rate); + printf("\tVolume: %.2f\n", master_volume); + printf("\tTime offset: %d seconds\n", offset); + printf("\tTest mode: %s\n", test_mode ? "Enabled" : "Disabled"); // Setup PulseAudio pa_buffer_attr output_buffer_atr = { @@ -288,11 +286,8 @@ int main(int argc, char **argv) { elapsed_samples = 0; sequence_completed = 0; - if (new_sequence == SEQ_29_56) { - total_sequence_samples = samples_29_56; - } else { - total_sequence_samples = samples_59_55; - } + if (new_sequence == SEQ_29_56) total_sequence_samples = samples_29_56; + else total_sequence_samples = samples_59_55; memset(output, 0, sizeof(output)); } else { @@ -313,9 +308,7 @@ int main(int argc, char **argv) { &elapsed_samples, total_sequence_samples, pip_samples, pause_samples, beep_samples, num_pips); - if (!playing_sequence && !sequence_completed) { - sequence_completed = 1; - } + if (!playing_sequence && !sequence_completed) sequence_completed = 1; if((pulse_error = write_PulseOutputDevice(&output_device, output, sizeof(output)))) { fprintf(stderr, "Error writing to output device: %s\n", pa_strerror(pulse_error)); diff --git a/src/dcf95.c b/src/dcf95.c index 4302670..ffdad9b 100644 --- a/src/dcf95.c +++ b/src/dcf95.c @@ -1,10 +1,10 @@ #include +#include #include #include #include #include #include -#include #define buffer_maxlength 2048 #define buffer_tlength_fragsize 2048 @@ -12,8 +12,8 @@ // #define DEBUG -#include "../lib/constants.h" -#include "../lib/oscillator.h" +#include "../dsp/constants.h" +#include "../dsp/oscillator.h" #define DEFAULT_FREQ 77500.0f #define DEFAULT_SAMPLE_RATE 192000 @@ -55,17 +55,12 @@ static void stop(int signum) { unsigned int generate_chip() { unsigned int chip = lfsr & 1; - lfsr >>= 1; - if (chip || !lfsr) - lfsr ^= 0x110; - + if (chip || !lfsr)lfsr ^= 0x110; return chip; } -void reset_lfsr() { - lfsr = 0; -} +void reset_lfsr() { lfsr = 0; } int is_cet_dst(struct tm *tm_time) { int month = tm_time->tm_mon + 1; @@ -74,16 +69,11 @@ int is_cet_dst(struct tm *tm_time) { if (month == 3) { int last_sunday = 31 - ((5 + 31) % 7); - if ((day > last_sunday) || (day == last_sunday && hour >= 2)) { - return 1; - } - } else if (month > 3 && month < 10) { - return 1; - } else if (month == 10) { + if ((day > last_sunday) || (day == last_sunday && hour >= 2)) return 1; + } else if (month > 3 && month < 10) return 1; + else if (month == 10) { int last_sunday = 31 - ((5 + 31) % 7); - if ((day < last_sunday) || (day == last_sunday && hour < 3)) { - return 1; - } + if ((day < last_sunday) || (day == last_sunday && hour < 3)) return 1; } return 0; @@ -132,41 +122,25 @@ void calculate_dcf77_bits(time_t now, int *bits) { bits[20] = 1; int minutes = t->tm_min; - for (int i = 0; i < 4; i++) { - bits[21 + i] = (minutes % 10 >> i) & 1; - } - for (int i = 0; i < 3; i++) { - bits[25 + i] = (minutes / 10 >> i) & 1; - } + for (int i = 0; i < 4; i++) bits[21 + i] = (minutes % 10 >> i) & 1; + for (int i = 0; i < 3; i++) bits[25 + i] = (minutes / 10 >> i) & 1; int minute_parity = 0; - for (int i = 21; i <= 27; i++) { - minute_parity ^= bits[i]; - } + for (int i = 21; i <= 27; i++) minute_parity ^= bits[i]; bits[28] = minute_parity; int hours = t->tm_hour; if(cest) hours += 1; - for (int i = 0; i < 4; i++) { - bits[29 + i] = (hours % 10 >> i) & 1; - } - for (int i = 0; i < 2; i++) { - bits[33 + i] = (hours / 10 >> i) & 1; - } + for (int i = 0; i < 4; i++) bits[29 + i] = (hours % 10 >> i) & 1; + for (int i = 0; i < 2; i++) bits[33 + i] = (hours / 10 >> i) & 1; int hour_parity = 0; - for (int i = 29; i <= 34; i++) { - hour_parity ^= bits[i]; - } + for (int i = 29; i <= 34; i++) hour_parity ^= bits[i]; bits[35] = hour_parity; int day = t->tm_mday; - for (int i = 0; i < 4; i++) { - bits[36 + i] = (day % 10 >> i) & 1; - } - for (int i = 0; i < 2; i++) { - bits[40 + i] = (day / 10 >> i) & 1; - } + for (int i = 0; i < 4; i++) bits[36 + i] = (day % 10 >> i) & 1; + for (int i = 0; i < 2; i++) bits[40 + i] = (day / 10 >> i) & 1; int dow = t->tm_wday == 0 ? 7 : t->tm_wday; bits[42] = dow & 0x01; @@ -174,23 +148,15 @@ void calculate_dcf77_bits(time_t now, int *bits) { bits[44] = (dow >> 2) & 0x01; int month = t->tm_mon + 1; - for (int i = 0; i < 4; i++) { - bits[45 + i] = (month % 10 >> i) & 1; - } + for (int i = 0; i < 4; i++) bits[45 + i] = (month % 10 >> i) & 1; bits[49] = (month / 10) & 0x01; int year = t->tm_year % 100; - for (int i = 0; i < 4; i++) { - bits[50 + i] = (year % 10 >> i) & 1; - } - for (int i = 0; i < 4; i++) { - bits[54 + i] = (year / 10 >> i) & 1; - } + for (int i = 0; i < 4; i++) bits[50 + i] = (year % 10 >> i) & 1; + for (int i = 0; i < 4; i++) bits[54 + i] = (year / 10 >> i) & 1; int year_parity = 0; - for (int i = 36; i <= 57; i++) { - year_parity ^= bits[i]; - } + for (int i = 36; i <= 57; i++) year_parity ^= bits[i]; bits[58] = year_parity; bits[59] = 2; @@ -200,7 +166,7 @@ void print_dcf77_bits(const int *bits) { printf("DCF77 Bit Pattern: "); for (int i = 0; i < 60; i++) { printf("%d", bits[i]); - if ((i+1) % 10 == 0) printf(" "); + if ((i+1) % 8 == 0) printf(" "); } printf("\n"); } @@ -237,10 +203,10 @@ int main(int argc, char **argv) { float master_volume = DEFAULT_MASTER_VOLUME; float freq = DEFAULT_FREQ; - int sample_rate = DEFAULT_SAMPLE_RATE; - int offset = DEFAULT_OFFSET; - int test_mode = 0; - int no_phase = 0; + uint32_t sample_rate = DEFAULT_SAMPLE_RATE; + uint8_t offset = DEFAULT_OFFSET; + uint8_t test_mode = 0; + uint8_t no_phase = 0; // #region Parse Arguments int opt; @@ -298,16 +264,13 @@ int main(int argc, char **argv) { } printf("Configuration:\n"); - printf(" Output device: %s\n", audio_output_device); - printf(" Frequency: %.1f Hz\n", freq); - printf(" Sample rate: %d Hz\n", sample_rate); - printf(" Volume: %.2f\n", master_volume); - printf(" Time offset: %d seconds\n", offset); - if (no_phase) { - printf(" Phase modulation: Disabled\n"); - } else { - printf(" Phase modulation: +/- %.1f degrees\n", PHASE_SHIFT); - } + printf("\tOutput device: %s\n", audio_output_device); + printf("\tFrequency: %.1f Hz\n", freq); + printf("\tSample rate: %d Hz\n", sample_rate); + printf("\tVolume: %.2f\n", master_volume); + printf("\tTime offset: %d seconds\n", offset); + if (no_phase) printf("\tPhase modulation: Disabled\n"); + else printf("\tPhase modulation: +/- %.1f degrees\n", PHASE_SHIFT); // #region Setup devices pa_buffer_attr output_buffer_atr = { @@ -416,11 +379,8 @@ int main(int argc, char **argv) { unsigned int modulated_chip = chip ^ dcf77_bits[current_bit]; - if (modulated_chip == 0) { - phase_offset = phase_shift_rad; - } else { - phase_offset = -phase_shift_rad; - } + if (modulated_chip == 0) phase_offset = phase_shift_rad; + else phase_offset = -phase_shift_rad; current_chip_count++; } @@ -437,12 +397,8 @@ int main(int argc, char **argv) { if ((dcf77_bits[current_bit] == 0 && ms_within_second < PULSE_0_DURATION) || (dcf77_bits[current_bit] == 1 && ms_within_second < PULSE_1_DURATION)) { output[i] = carrier * master_volume * REDUCED_AMPLITUDE; - } else { - output[i] = carrier * master_volume; - } - } else { - output[i] = carrier * master_volume; - } + } else output[i] = carrier * master_volume; + } else output[i] = carrier * master_volume; elapsed_samples++; } diff --git a/src/fm95.c b/src/fm95.c index 31d441a..e11b69b 100644 --- a/src/fm95.c +++ b/src/fm95.c @@ -1,5 +1,6 @@ #include #include +#include #include #define buffer_maxlength 12288 @@ -16,12 +17,12 @@ #define DEFAULT_MPX_POWER 3.0f // dbr, this is for BS412, simplest bs412 #define DEFAULT_MPX_DEVIATION 75000.0f // for BS412 -#include "../lib/oscillator.h" -#include "../lib/filters.h" -#include "../lib/fm_modulator.h" +#include "../dsp/oscillator.h" +#include "../dsp/filters.h" +#include "../dsp/fm_modulator.h" #include "../lib/optimization.h" -#include "../lib/bs412.h" -#include "../lib/gain_control.h" +#include "../dsp/bs412.h" +#include "../dsp/gain_control.h" #define DEFAULT_SAMPLE_RATE 192000 @@ -29,7 +30,7 @@ #define OUTPUT_DEVICE "alsa_output.platform-soc_sound.stereo-fallback" #define RDS_DEVICE "RDS.monitor" #define MPX_DEVICE "FM_MPX.monitor" -// #define SCA_DEVICE "" +#define SCA_DEVICE "\0" // Disabled #define BUFFER_SIZE 2048 @@ -76,7 +77,7 @@ static void stop(int signum) { } void show_version() { - printf("fm95 (an FM Processor by radio95) version 1.5\n"); + printf("fm95 (an FM Processor by radio95) version 1.6\n"); } void show_help(char *name) { printf( @@ -139,8 +140,8 @@ int main(int argc, char **argv) { PulseOutputDevice output_device; float clipper_threshold = DEFAULT_CLIPPER_THRESHOLD; - int stereo = DEFAULT_STEREO; - int polar_stereo = DEFAULT_STEREO_POLAR; + uint8_t stereo = DEFAULT_STEREO; + uint8_t polar_stereo = DEFAULT_STEREO_POLAR; float sca_frequency = DEFAULT_SCA_FREQUENCY; float sca_deviation = DEFAULT_SCA_DEVIATION; @@ -148,30 +149,18 @@ int main(int argc, char **argv) { char audio_input_device[64] = INPUT_DEVICE; char audio_output_device[64] = OUTPUT_DEVICE; -#ifndef MPX_DEVICE - char audio_mpx_device[64] = "\0"; -#else char audio_mpx_device[64] = MPX_DEVICE; -#endif -#ifndef RDS_DEVICE - char audio_rds_device[64] = "\0"; -#else char audio_rds_device[64] = RDS_DEVICE; -#endif -#ifndef SCA_DEVICE - char audio_sca_device[64] = "\0"; -#else char audio_sca_device[64] = SCA_DEVICE; -#endif float preemphasis_tau = DEFAULT_PREEMPHASIS_TAU; - int calibration_mode = 0; + uint8_t calibration_mode = 0; float mpx_power = DEFAULT_MPX_POWER; float mpx_deviation = DEFAULT_MPX_DEVIATION; float master_volume = DEFAULT_MASTER_VOLUME; float audio_volume = DEFAULT_AUDIO_VOLUME; - int sample_rate = DEFAULT_SAMPLE_RATE; + uint32_t sample_rate = DEFAULT_SAMPLE_RATE; // #region Parse Arguments int opt; @@ -203,11 +192,8 @@ int main(int argc, char **argv) { while((opt = getopt_long(argc, argv, short_opt, long_opt, NULL)) != -1) { switch(opt) { case 's': // Stereo - if(optarg) { - stereo = atoi(optarg); - } else { - stereo = 1; - } + if(optarg) stereo = atoi(optarg); + else stereo = 1; break; case 'i': // Input Device memcpy(audio_input_device, optarg, 63); @@ -237,11 +223,8 @@ int main(int argc, char **argv) { clipper_threshold = strtof(optarg, NULL); break; case 'P': //Polar - if(optarg) { - polar_stereo = atoi(optarg); - } else { - polar_stereo = 1; - } + if(optarg) polar_stereo = atoi(optarg); + else polar_stereo = 1; break; case 'R': // Preemp preemphasis_tau = strtof(optarg, NULL)*0.000001; @@ -356,9 +339,7 @@ int main(int argc, char **argv) { float output[BUFFER_SIZE]; while(to_run) { - for (int i = 0; i < BUFFER_SIZE; i++) { - output[i] = get_oscillator_sin_sample(&osc)*master_volume; - } + for (int i = 0; i < BUFFER_SIZE; i++) output[i] = get_oscillator_sin_sample(&osc)*master_volume; if((pulse_error = write_PulseOutputDevice(&output_device, output, sizeof(output)))) { // get output from the function and assign it into pulse_error, this comment to avoid confusion fprintf(stderr, "Error writing to output device: %s\n", pa_strerror(pulse_error)); to_run = 0; @@ -463,9 +444,8 @@ int main(int argc, char **argv) { float stereo = (ready_l - ready_r) / 2.0f; stereo_carrier = get_oscillator_sin_multiplier_ni(&osc, polar_stereo ? 1 : 8); - if(polar_stereo) { - audio += ((stereo+0.2)*stereo_carrier)*STEREO_VOLUME; - } else { + if(polar_stereo) audio += ((stereo+0.2)*stereo_carrier)*STEREO_VOLUME; + else { float pilot = get_oscillator_sin_multiplier_ni(&osc, 4); mpx += pilot*PILOT_VOLUME; audio += (stereo*stereo_carrier)*STEREO_VOLUME; @@ -484,13 +464,12 @@ int main(int argc, char **argv) { float mpx_only = measure_mpx(&mpx_only_power, mpx * mpx_deviation); float mpower = measure_mpx(&power, (audio+mpx) * mpx_deviation); - mpower = deviation_to_dbr(dbr_to_deviation(mpower) - dbr_to_deviation(mpx_only)); if (mpower > mpx_power) { - float excess_power = mpower - mpx_power; - audio *= (dbr_to_deviation(-excess_power)/mpx_deviation); + float excess_power = mpower - mpx_only - mpx_power; // Make sure that MPX doesn't affect the audio + audio *= (dbr_to_deviation(-excess_power)/mpx_deviation); // This should be more dynamic, but too bad } - audio = hard_clip(audio, 1-mpx); + audio = hard_clip(audio, 1-mpx); // Prevent clipping, via clipping the audio signal with relation to the mpx signal output[i] = (audio+mpx)*master_volume; if(rds_on || stereo) advance_oscillator(&osc);