Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions tests/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -249,3 +249,12 @@ test_tonal_reducer = executable('test_tonal_reducer',
include_directories: [inc, src_inc]
)
test('tonal_reducer', test_tonal_reducer)

test_simd_utils = executable('test_simd_utils',
sources: ['test_simd_utils.c'],
dependencies: [libspecbleach_dep, m_dep],
c_args: test_c_args,
link_args: test_link_args,
include_directories: [inc, src_inc]
)
test('simd_utils', test_simd_utils)
224 changes: 223 additions & 1 deletion tests/test_brandt_noise_estimator.c
Original file line number Diff line number Diff line change
Expand Up @@ -129,13 +129,235 @@ void test_brandt_state_management(void) {
printf("✓ Brandt state management tests passed\n");
}

void test_brandt_convergence(void) {
printf("Testing Brandt convergence over multiple frames...\n");

uint32_t real_size = 64;
uint32_t sr = 44100;
uint32_t fft_size = 128;

BrandtNoiseEstimator* est =
brandt_noise_estimator_initialize(real_size, 500.0f, sr, fft_size);

float* spectrum = (float*)calloc(real_size, sizeof(float));
float* noise_spectrum = (float*)calloc(real_size, sizeof(float));

// Initialize with a known noise floor
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 0.1f + (float)i * 0.01f; // Increasing noise floor
}
brandt_noise_estimator_set_state(est, spectrum);

// Run multiple frames with same noise level
for (int frame = 0; frame < 50; frame++) {
// Add small variations to simulate noise
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 0.1f + (float)i * 0.01f + 0.02f * sinf((float)frame * 0.1f);
}
brandt_noise_estimator_run(est, spectrum, noise_spectrum);
}

// After convergence, noise estimate should be reasonable
for (uint32_t i = 0; i < real_size; i++) {
TEST_ASSERT(noise_spectrum[i] >= 0.05f && noise_spectrum[i] <= 0.5f,
"Converged noise estimate should be in reasonable range");
}

free(spectrum);
free(noise_spectrum);
brandt_noise_estimator_free(est);
printf("✓ Brandt convergence tests passed\n");
}

void test_brandt_varying_energy_levels(void) {
printf("Testing Brandt with varying energy levels...\n");

uint32_t real_size = 32;
uint32_t sr = 44100;
uint32_t fft_size = 64;

BrandtNoiseEstimator* est =
brandt_noise_estimator_initialize(real_size, 300.0f, sr, fft_size);

float* spectrum = (float*)calloc(real_size, sizeof(float));
float* noise_spectrum = (float*)calloc(real_size, sizeof(float));

// Initialize with moderate energy
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 1.0f;
}
brandt_noise_estimator_set_state(est, spectrum);

// Test with very low energy (should handle gracefully)
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 1e-8f;
}
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle very low energy");

// Test with high energy
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 100.0f;
}
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle high energy");

// Test with mixed energy levels
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = (i % 2 == 0) ? 0.01f : 10.0f;
}
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle mixed energy levels");

free(spectrum);
free(noise_spectrum);
brandt_noise_estimator_free(est);
printf("✓ Brandt varying energy level tests passed\n");
}

void test_brandt_spectral_patterns(void) {
printf("Testing Brandt with different spectral patterns...\n");

uint32_t real_size = 64;
uint32_t sr = 44100;
uint32_t fft_size = 128;

BrandtNoiseEstimator* est =
brandt_noise_estimator_initialize(real_size, 400.0f, sr, fft_size);

float* spectrum = (float*)calloc(real_size, sizeof(float));
float* noise_spectrum = (float*)calloc(real_size, sizeof(float));

// Test 1: Flat spectrum
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 1.0f;
}
brandt_noise_estimator_set_state(est, spectrum);
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle flat spectrum");

// Test 2: Sloped spectrum (pink noise like)
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 1.0f / sqrtf((float)(i + 1));
}
brandt_noise_estimator_set_state(est, spectrum);
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle sloped spectrum");

// Test 3: Peaked spectrum (tonal components)
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 0.1f;
if (i == 10 || i == 30 || i == 50) {
spectrum[i] = 5.0f; // Peaks
}
}
brandt_noise_estimator_set_state(est, spectrum);
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle peaked spectrum");

// Test 4: Decaying spectrum
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = expf(-(float)i * 0.05f);
}
brandt_noise_estimator_set_state(est, spectrum);
TEST_ASSERT(brandt_noise_estimator_run(est, spectrum, noise_spectrum),
"Should handle decaying spectrum");

free(spectrum);
free(noise_spectrum);
brandt_noise_estimator_free(est);
printf("✓ Brandt spectral pattern tests passed\n");
}

void test_brandt_history_duration(void) {
printf("Testing Brandt with different history durations...\n");

uint32_t real_size = 32;
uint32_t sr = 44100;
uint32_t fft_size = 64;

// Test short history
BrandtNoiseEstimator* est_short =
brandt_noise_estimator_initialize(real_size, 100.0f, sr, fft_size);
TEST_ASSERT(est_short != NULL, "Short history initialization should succeed");
brandt_noise_estimator_free(est_short);

// Test medium history
BrandtNoiseEstimator* est_med =
brandt_noise_estimator_initialize(real_size, 500.0f, sr, fft_size);
TEST_ASSERT(est_med != NULL, "Medium history initialization should succeed");
brandt_noise_estimator_free(est_med);

// Test long history
BrandtNoiseEstimator* est_long =
brandt_noise_estimator_initialize(real_size, 2000.0f, sr, fft_size);
TEST_ASSERT(est_long != NULL, "Long history initialization should succeed");
brandt_noise_estimator_free(est_long);

// Test very short history (edge case)
BrandtNoiseEstimator* est_vshort =
brandt_noise_estimator_initialize(real_size, 10.0f, sr, fft_size);
TEST_ASSERT(est_vshort != NULL,
"Very short history initialization should succeed");
brandt_noise_estimator_free(est_vshort);

printf("✓ Brandt history duration tests passed\n");
}

void test_brandt_floor_application(void) {
printf("Testing Brandt floor application behavior...\n");

uint32_t real_size = 32;
uint32_t sr = 44100;
uint32_t fft_size = 64;

BrandtNoiseEstimator* est =
brandt_noise_estimator_initialize(real_size, 300.0f, sr, fft_size);

float* spectrum = (float*)calloc(real_size, sizeof(float));
float* noise_spectrum = (float*)calloc(real_size, sizeof(float));
float* floor_profile = (float*)calloc(real_size, sizeof(float));

// Initialize with low noise
for (uint32_t i = 0; i < real_size; i++) {
spectrum[i] = 0.1f;
}
brandt_noise_estimator_set_state(est, spectrum);

// Apply floor higher than current estimate
for (uint32_t i = 0; i < real_size; i++) {
floor_profile[i] = 0.5f;
}
brandt_noise_estimator_apply_floor(est, floor_profile);

// Run estimation - should respect the floor
brandt_noise_estimator_run(est, spectrum, noise_spectrum);

// Check that estimate is influenced by floor
for (uint32_t i = 0; i < real_size; i++) {
TEST_ASSERT(noise_spectrum[i] >= 0.0f,
"Noise estimate should be non-negative after floor");
}

free(spectrum);
free(noise_spectrum);
free(floor_profile);
brandt_noise_estimator_free(est);
printf("✓ Brandt floor application tests passed\n");
}

int main(void) {
printf("Running Brandt Noise Estimator tests...\n\n");

test_brandt_initialization();
test_brandt_run_logic();
test_brandt_state_management();
test_brandt_convergence();
test_brandt_varying_energy_levels();
test_brandt_spectral_patterns();
test_brandt_history_duration();
test_brandt_floor_application();

printf("\n✅ All Brandt tests passed!\n");
return 0;
}
}
Loading
Loading