Commit ead310a4 authored by Jan Kiene's avatar Jan Kiene
Browse files

add ssnr to test_param_fle tests

parent a7b7c462
Loading
Loading
Loading
Loading
+20 −5
Original line number Diff line number Diff line
@@ -232,6 +232,7 @@ def compare(
    fs: int,
    per_frame: bool = True,
    get_mld: bool = False,
    get_ssnr: bool = False,
) -> dict:
    """Compare two audio arrays

@@ -266,8 +267,13 @@ def compare(
        "first_diff_pos_sample": -1,
        "first_diff_pos_channel": -1,
        "first_diff_pos_frame": -1,
        "MLD": 0 if get_mld else None,
    }

    if get_mld:
        result["MLD"] = 0
    if get_ssnr:
        result["SSNR"] = np.zeros(ref.shape[1])

    if per_frame:
        result["max_abs_diff_pos_frame"] = 0
        result["nframes_diff"] = 0
@@ -320,7 +326,6 @@ def compare(
            result["nframes_diff_percentage"] = nframes_diff_percentage

        if get_mld:

            mld_max = 0
            toolsdir = Path(__file__).parent.parent.joinpath("tools")
            if platform.system() == "Windows":
@@ -343,6 +348,12 @@ def compare(

            result["MLD"] = mld_max

        if get_ssnr:
            # length of segment is always 20ms
            len_seg = int(0.02 * fs)
            print(len_seg, ref.shape, test.shape)
            result["SSNR"] = ssnr(ref, test, len_seg, thresh_low=-50, thresh_high=-15)

    return result


@@ -527,11 +538,14 @@ def ssnr(
    """
    ss = list()

    ref_sig_norm = ref_sig / -np.iinfo(np.int16).min
    test_sig_norm = test_sig / -np.iinfo(np.int16).min

    denom_add = 10**-13 * len_seg
    segment_counter = np.zeros(ref_sig.shape[1])
    for ref_seg, test_seg in zip(
        get_framewise(ref_sig, len_seg, zero_pad=True),
        get_framewise(test_sig, len_seg, zero_pad=True),
        get_framewise(ref_sig_norm, len_seg, zero_pad=True),
        get_framewise(test_sig_norm, len_seg, zero_pad=True),
    ):
        nrg_ref = np.sum(ref_seg**2, axis=0)

@@ -551,5 +565,6 @@ def ssnr(

        ss.append(ss_seg)

    ssnr = 10 * np.log10(10 ** (np.sum(ss, axis=0) / segment_counter) - 1)
    # round to 2 decimals. this is just to be in line with the meg conformance tool
    ssnr = np.round(10 * np.log10(10 ** (np.sum(ss, axis=0) / segment_counter) - 1), 2)
    return ssnr
+2 −12
Original line number Diff line number Diff line
import argparse
import sys
import pathlib
import numpy as np
from pyaudio3dtools import audiofile, audioarray


THRESH_LOW = -50
THRESH_HIGH = -15


def main(args):
    ref_sig, fs_ref = audiofile.readfile(args.ref_file)
    test_sig, fs_test = audiofile.readfile(args.test_file)
@@ -17,14 +12,9 @@ def main(args):
        print("Files need to have same sampling rate!")
        return -1

    # normalize 16Bit wav signals to range of [-1, 1]
    ref_sig /= -np.iinfo(np.int16).min
    test_sig /= -np.iinfo(np.int16).min

    len_seg = int(20 * fs_ref / 1000)
    ssnr = audioarray.ssnr(
        ref_sig, test_sig, len_seg, thresh_low=THRESH_LOW, thresh_high=THRESH_HIGH
    )
    print(len_seg, ref_sig.shape, test_sig.shape)
    ssnr = audioarray.ssnr(ref_sig, test_sig, len_seg, thresh_low=-50, thresh_high=-15)

    for i, s in enumerate(ssnr, start=1):
        print(f"Channel {i}: {s}")
+12 −7
Original line number Diff line number Diff line
@@ -13,14 +13,15 @@ import pyivastest


def cmp_pcm(
    file1,
    file2,
    ref_file,
    cmp_file,
    out_config,
    fs,
    get_mld=False,
    allow_differing_lengths=False,
    mld_lim=0,
    abs_tol=0,
    get_ssnr=False,
) -> (int, str):
    """
    Compare 2 PCM files for bitexactness
@@ -39,8 +40,8 @@ def cmp_pcm(
    else:
        nchannels = pyivastest.constants.OC_TO_NCHANNELS[out_config.upper()]

    s1, _ = pyaudio3dtools.audiofile.readfile(file1, nchannels, fs, outdtype=np.int16)
    s2, _ = pyaudio3dtools.audiofile.readfile(file2, nchannels, fs, outdtype=np.int16)
    s1, _ = pyaudio3dtools.audiofile.readfile(ref_file, nchannels, fs, outdtype=np.int16)
    s2, _ = pyaudio3dtools.audiofile.readfile(cmp_file, nchannels, fs, outdtype=np.int16)

    # In case of wav input, override the nchannels with the one from the wav header
    nchannels = s1.shape[1]
@@ -62,7 +63,7 @@ def cmp_pcm(
        return 1, reason

    cmp_result = pyaudio3dtools.audioarray.compare(
        s1, s2, fs, per_frame=False, get_mld=get_mld
        s1, s2, fs, per_frame=False, get_mld=get_mld, get_ssnr=get_ssnr,
    )

    output_differs = 0
@@ -90,13 +91,17 @@ def cmp_pcm(
        else:
            reason += f" > {mld_lim}"

    if get_ssnr:
        for i, s in enumerate(cmp_result["SSNR"], start=1):
            print(f"Channel {i} SSNR: {s}")

    return output_differs, reason


if __name__ == "__main__":
    parser = argparse.ArgumentParser()
    parser.add_argument("file1", type=str)
    parser.add_argument("file2", type=str)
    parser.add_argument("ref_file", type=str)
    parser.add_argument("cmp_file", type=str)
    parser.add_argument(
        "-o",
        "--out_config",
+3 −1
Original line number Diff line number Diff line
@@ -152,6 +152,7 @@ def test_param_file_tests(
    get_mld,
    get_mld_lim,
    abs_tol,
    get_ssnr,
):
    enc_opts, dec_opts, sim_opts, eid_opts = param_file_test_dict[test_tag]

@@ -341,14 +342,15 @@ def test_param_file_tests(

        fs = int(sampling_rate) * 1000
        output_differs, reason = cmp_pcm(
            dut_output_file,
            ref_output_file,
            dut_output_file,
            output_config,
            fs,
            get_mld=get_mld,
            mld_lim=get_mld_lim,
            abs_tol=abs_tol,
            allow_differing_lengths=allow_differing_lengths,
            get_ssnr=get_ssnr,
        )
        md_out_files = get_expected_md_files(ref_output_file, enc_split, output_config)

+15 −0
Original line number Diff line number Diff line
@@ -171,6 +171,13 @@ def pytest_addoption(parser):
        help="MLD limit for comparison (default: 0)",
        default="0",
    )

    parser.addoption(
        "--ssnr",
        action="store_true",
        help="Compute Segmental SNR (SSNR) between ref and dut output instead of just comparing for bitexactness",
    )

    parser.addoption(
        "--create_ref",
        action="store_true",
@@ -242,6 +249,14 @@ def get_mld_lim(request):
    return float(request.config.getoption("--mld-lim"))


@pytest.fixture(scope="session", autouse=True)
def get_ssnr(request):
    """
    Return indication to compute ssnr during ref/dut comparison.
    """
    return request.config.option.ssnr


@pytest.fixture(scope="session")
def abs_tol(request) -> int:
    """