Just sharing my Distortion SSE code


#1

input should be 16 bits aligned so it will work correctly.
drive is from 0 to 4, or even higher.
So, it is like this:

float input[4];
float drive;

// (((sqrt(input) - input) * drive) + input)  *  (1 - ((drive / 4) * 0.5))

__m128 dinput = _mm_load_ps(input);
__m128 mask = _mm_add_ps(_mm_and_ps(_mm_set1_ps(-2.0f),
    _mm_cmpnge_ps(dinput, _mm_setzero_ps())), _mm_set1_ps(1.0f));
__m128 ddrive = _mm_set1_ps(drive);
__m128 sqrtInput = _mm_mul_ps(_mm_sqrt_ps(_mm_mul_ps(dinput, mask)), mask);
__m128 result1 = _mm_add_ps(_mm_mul_ps(_mm_sub_ps(sqrtInput, dinput), ddrive), dinput);
_mm_store_ps(input,
    _mm_mul_ps(result1,
    _mm_sub_ps(_mm_set1_ps(1.0f), _mm_mul_ps(_mm_div_ps(ddrive, _mm_set1_ps(4.0f)), _mm_set1_ps(0.5f)))));

#2

Thanks for sharing!

I tried doing it just regular old c++

output = (((sqrt(input) - input) * drive) + input)  *  (1 - ((drive / 4) * 5));//

...and it kind of blew up and killed my audio, even if I scale it way down. I'm not up on SSE so I'm not sure if you are doing something else there, but just wanted to share my experience, as I'm really into different ways to do distortion.

Thanks


#3

Thanks! And yes, I forgot to mention that the C++ code you need to be carefull with the sqrt, as you can't put negatives there. I usually just do this: if (input < 0) -sqrt(-input) - this is included in the SSE code.


#4

I also fixed the regular C++ math above, I made a mistake when I copied it over... <shame face>


// (((sqrt(input) - input) * drive) + input) * (1 - ((drive / 4) * 0.5))
 

The last number is not 5, but 0.5