Page 1 of 1

how to DSP-code "signed square root"?

PostPosted: Wed Mar 18, 2020 1:05 pm
by steph_tsf
if x positive
then x = sqrt(x)
else x = - (sqrt (-x))
end

I've just completed a 64-tap Widrow-Hoff LMS Machinery. It is written in DSP (not in Green, not in Ruby, not in x86 Assembly). The "textbook" variant is doing fine. I would like to experiment a "signed square root" variant, that's "softening" the error signal using the above mentioned "signed square root" function, and also "softening" the incoming signal, before one is combining them using a multiplication.

Code: Select all
mu2err = mu * 2.0 * err;
a00=leak*(a00+(mu2err * m00));
a01=leak*(a01+(mu2err * m01));
a02=leak*(a02+(mu2err * m02));
a03=leak*(a03+(mu2err * m03));
a04=leak*(a04+(mu2err * m04));

Thus, I need to compute :
a00=leak*(a00+SIGNEDSQUAREROOT(mu2err * m00));
a01=leak*(a01+SIGNEDSQUAREROOT(mu2err * m01));
etc.

intelliger 64 v1.0 leaky.fsm
(2.11 MiB) Downloaded 1047 times

intelliger 64 v1.0 leaky.jpg (650 pix).jpg
intelliger 64 v1.0 leaky.jpg (650 pix).jpg (74.96 KiB) Viewed 14641 times

Any help much appreciated
Have a nice day

Re: how to DSP-code "signed square root"?

PostPosted: Wed Mar 18, 2020 3:28 pm
by pshannon
Just taking a jab here. Did you actually check the results of X? When you expect a negative signed result, are you actually getting this? Sometimes if then and variable assignments have given me incorrect results and I created a work around for testing to see if the added steps resolve the issue even though the logic appears 100% correct. I am only assuming your equation is 100% correct and should work. The other Assumption: if x positive true/false works? I did not try your attached .fsm and if I am way off base, my bad. I am only trying to give you ideas.
Below will force signed x.

Try x=sqrt(x*-1.0) * -1.0
and/or
if x<0 then
x = - (sqrt (-x))
else
x = sqrt(x)
end

Re: how to DSP-code "signed square root"?

PostPosted: Wed Mar 18, 2020 8:40 pm
by martinvicanek
In code:
Code: Select all
streamin x;
streamout y;

float abs, sgn        // bitmasks

stage(0){
  abs = 3.2|1.4;      //  abs bitmask 01111111 11111111 11111111 11111111
  sgn = -0;           // sign bitmask 10000000 00000000 00000000 00000000
  }

stage(2){
  y = (sgn&x)|sqrt(abs&x);
  }


ASM:
Code: Select all
streamin x;
streamout y;

int abs=2147483647;  //  abs bitmask 01111111 11111111 11111111 11111111
int sgn=-2147483648; // sign bitmask 10000000 00000000 00000000 00000000

movaps xmm0,abs;
andps xmm0,x;
sqrtps xmm0,xmm0;
movaps xmm1,sgn;
andps xmm1,x;
orps xmm1,xmm0;
movaps y,xmm1;


Re: how to DSP-code "signed square root"?

PostPosted: Wed Mar 18, 2020 9:37 pm
by steph_tsf
pshannon wrote:Try x=sqrt(x*-1.0) * -1.0
Unfortunately, I don't understand your suggestion. In Flowstone DSP Code Component, conditional statements must be implemented using a mask.
For example, the following Flowstone DSP Code: x = x - (x >= 1) & 1.0;
is equivalent to the following C/C++ code: if( x >= 1 ) x = x – 1.0;

The following cumbersome Flowstone DSP code is doing what I am requiring:

Code: Select all
streamin x;
streamout y;
y=sqrt(abs(x))*(((x<0)&-1.0)+(x>0)&1.0);

The corresponding assembly code is:

Code: Select all
streamin x;streamout y;float smIntVarTemp=0.0;
float smIntVarZero=0;
float F0=0;
float FM1=-1;
float F1=1;
movaps xmm0,x;
movaps smIntVarTemp,xmm0;
cmpps xmm0,smIntVarZero,6;
andps xmm0,smIntVarTemp;
addps xmm0,xmm0;
subps xmm0,smIntVarTemp;
sqrtps xmm0,xmm0;
movaps xmm1,x;
cmpps xmm1,F0,1;
movaps xmm2,xmm1;
andps xmm2,FM1;
movaps xmm3,x;
cmpps xmm3,F0,6;
movaps xmm4,xmm3;
andps xmm4,F1;
addps xmm2,xmm4;
mulps xmm0,xmm2;
//Assignment> sLeft=xmm0
movaps y,xmm0;

Looks like a joke
Is there a more efficient approach, still in Flowstone DSP Code Component?
Any help much appreciated

Re: how to DSP-code "signed square root"?

PostPosted: Wed Mar 18, 2020 10:04 pm
by steph_tsf
Martin, I didn't notice your kind reply dated Wed Mar 18, 2020 9:40 pm.
Looks brilliant.

Code: Select all
a00=leak*(a00+(mu2err * m00));
a01=leak*(a01+(mu2err * m01));
a02=leak*(a02+(mu2err * m02));
etc.

can thus become in stage (2):

Code: Select all
x=mu2err*m00;
a00=leak*(a00+((sgn&x)|sqrt(abs&x)));
x=mu2err*m01;
a01=leak*(a01+((sgn&x)|sqrt(abs&x)));
x=mu2err*m02;
a02=leak*(a02+((sgn&x)|sqrt(abs&x)));
etc.

Is it possible to also pipe-line the various mu2err*m00, mu2err*m01, etc. calculations, for regaining a "single line" layout?

Re: how to DSP-code "signed square root"?

PostPosted: Wed Mar 18, 2020 10:31 pm
by pshannon
When I responded it was to quickly and I thought it was a logic issue you were having or the signed x was not working correctly. I was leaning towards a bug in FS at first. I still know C & ASM, but I have not worked with the DSP code side yet. Sorry for the confusion.

Re: how to DSP-code "signed square root"?

PostPosted: Thu Mar 19, 2020 11:07 am
by steph_tsf
pshannon wrote:I have not worked with the DSP code side yet.
Me to. This is the first time I am digging into Flowstone DSP Code Component, deeper than computing y = a * x + b.

Attached, is a working implementation of Martin Vicanek solution:
signed square root.fsm
(8.18 KiB) Downloaded 1056 times

http://www.dsprobotics.com/Files/V3/User%20Guide.pdf chapter 9 page 240 doesn't list:
- the "vertical bar" operator,
- the "abs" (absolute value) function,
- the "square root" (sqrt) function.
Question: Is there a supported operators list somewhere?
Question: Is there a supported functions list somewhere?

Upon reading page 242, I realized that one can declare and access indexed arrays.
Question: is this really supported, and reliable, because on Flowstone 3.0.4, this appears to be not supported.
Question: can somebody please publish a circular buffer management example, whose length is 64?

Upon reading page 243, I realized that memin() creates a Mem type connector on the component so that one can pass in data from outside.
Question: is this really supported, and reliable, because on Flowstone 3.0.4, this appears to be not supported.
Question: can somebody please publish a memin() example?
Question: is there a memout()?

Upon reading page 243, I realized one can program loops.
Question: Is it allowed to rely on a loop counter, that's a variable instead of a constant?

Considering the lack of "normal" conditional statements in DSP coding, what Google search keyword do I need to specify for locating the utility that's converting a "if (condition) then (true branch) else (false branch) end" code sequence into a DSP code sequence?

Any help, much appreciated
Have a nice day