From 5a3e8b38bed3a3aedea54fec39125772fc247824 Mon Sep 17 00:00:00 2001 From: TimothyLottes Date: Tue, 8 Nov 2016 21:22:35 -0500 Subject: [PATCH] Add files via upload --- 20161018.html | 118 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 118 insertions(+) create mode 100644 20161018.html diff --git a/20161018.html b/20161018.html new file mode 100644 index 0000000..180727a --- /dev/null +++ b/20161018.html @@ -0,0 +1,118 @@ +
+

20161018 - Fixed Point Rounding

+
+
On the list of things to relearn for FPGA based machines.
+
+Round Half Away From Zero +
+
if(x>=0) x++; // cin in second example
+x+=(1<<(n-1))-1; // c input in second example
+x>>=n;
+
+Above is what I believe is the correct round half away from zero logic when shifting right by 'n' for signed integers. +This can be implemented in the FPGA DSP rather easily. +The CIN (carry in) can take either the inverted sign of P (dsp output feed back in the next cycle), +or the inverted sign of a*b. +DSP can do the following {multiply, round, shift} at a throughput of 0.5 clocks. +
+
+
+p=a*b+cin+c; // throughput of one clock
+p=p>>17; // gets dedicated forwarding path, can optionally add or subtract in same cycle
+
+Full table for 3-bit signed numbers a*b multiply with round away from zero before shift right by 2, +
+
+
a    b       float   int   binary      a*b+cin   +round     output
+------------------------   ------------------------------------------
+-4 * -1.00 =  4.00 ->  4   100 * 100 = 010001 -> 0010010 -> 0100 =  4 (overflows) 
+-4 * -0.75 =  3.00 ->  3   100 * 101 = 001101 -> 0001110 -> 0011 =  3
+-4 * -0.50 =  2.00 ->  2   100 * 110 = 001001 -> 0001010 -> 0010 =  2
+-4 * -0.25 =  1.00 ->  1   100 * 111 = 000101 -> 0000110 -> 0001 =  1
+-4 *  0.00 = -0.00 ->  0   100 * 000 = 000001 -> 0000010 -> 0000 =  0
+-4 *  0.25 = -1.00 -> -1   100 * 001 = 111100 -> 1111101 -> 1111 = -1
+-4 *  0.50 = -2.00 -> -2   100 * 010 = 111000 -> 1111001 -> 1110 = -2
+-4 *  0.75 = -3.00 -> -3   100 * 011 = 110100 -> 1110101 -> 1101 = -3
+------------------------   ------------------------------------------
+-3 * -1.00 =  3.00 ->  3   101 * 100 = 001101 -> 0001110 -> 0011 =  3
+-3 * -0.75 =  2.25 ->  2   101 * 101 = 001010 -> 0001011 -> 0010 =  2
+-3 * -0.50 =  1.50 ->  2   101 * 110 = 000111 -> 0001000 -> 0010 =  2
+-3 * -0.25 =  0.75 ->  1   101 * 111 = 000100 -> 0000101 -> 0001 =  1
+-3 *  0.00 = -0.00 ->  0   101 * 000 = 000001 -> 0000010 -> 0000 =  0
+-3 *  0.25 = -0.75 -> -1   101 * 001 = 111101 -> 1111110 -> 1111 = -1
+-3 *  0.50 = -1.50 -> -2   101 * 010 = 111010 -> 1111011 -> 1110 = -2
+-3 *  0.75 = -2.25 -> -2   101 * 011 = 110111 -> 1111000 -> 1110 = -2
+------------------------   ------------------------------------------
+-2 * -1.00 =  2.00 ->  2   110 * 100 = 001001 -> 0001010 -> 0010 =  2
+-2 * -0.75 =  1.50 ->  2   110 * 101 = 000111 -> 0001000 -> 0010 =  2
+-2 * -0.50 =  1.00 ->  1   110 * 110 = 000101 -> 0000110 -> 0001 =  1
+-2 * -0.25 =  0.50 ->  1   110 * 111 = 000011 -> 0000100 -> 0001 =  1
+-2 *  0.00 = -0.00 ->  0   110 * 000 = 000001 -> 0000010 -> 0000 =  0
+-2 *  0.25 = -0.50 -> -1   110 * 001 = 111110 -> 1111111 -> 1111 = -1
+-2 *  0.50 = -1.00 -> -1   110 * 010 = 111100 -> 1111101 -> 1111 = -1
+-2 *  0.75 = -1.50 -> -2   110 * 011 = 111010 -> 1111011 -> 1110 = -2
+------------------------   ------------------------------------------
+-1 * -1.00 =  1.00 ->  1   111 * 100 = 000101 -> 0000110 -> 0001 =  1
+-1 * -0.75 =  0.75 ->  1   111 * 101 = 000100 -> 0000101 -> 0001 =  1
+-1 * -0.50 =  0.50 ->  1   111 * 110 = 000011 -> 0000100 -> 0001 =  1
+-1 * -0.25 =  0.25 ->  0   111 * 111 = 000010 -> 0000011 -> 0000 =  0
+-1 *  0.00 = -0.00 ->  0   111 * 000 = 000001 -> 0000010 -> 0000 =  0
+-1 *  0.25 = -0.25 ->  0   111 * 001 = 111111 -> 0000000 -> 0000 =  0
+-1 *  0.50 = -0.50 -> -1   111 * 010 = 111110 -> 1111111 -> 1111 = -1
+-1 *  0.75 = -0.75 -> -1   111 * 011 = 111101 -> 1111110 -> 1111 = -1
+------------------------   ------------------------------------------
+ 0 * -1.00 = -0.00 ->  0   000 * 100 = 000001 -> 0000010 -> 0000 =  0
+ 0 * -0.75 = -0.00 ->  0   000 * 101 = 000001 -> 0000010 -> 0000 =  0
+ 0 * -0.50 = -0.00 ->  0   000 * 110 = 000001 -> 0000010 -> 0000 =  0
+ 0 * -0.25 = -0.00 ->  0   000 * 111 = 000001 -> 0000010 -> 0000 =  0
+ 0 *  0.00 =  0.00 ->  0   000 * 000 = 000001 -> 0000010 -> 0000 =  0
+ 0 *  0.25 =  0.00 ->  0   000 * 001 = 000001 -> 0000010 -> 0000 =  0
+ 0 *  0.50 =  0.00 ->  0   000 * 010 = 000001 -> 0000010 -> 0000 =  0
+ 0 *  0.75 =  0.00 ->  0   000 * 011 = 000001 -> 0000010 -> 0000 =  0
+------------------------   ------------------------------------------
+ 1 * -1.00 = -1.00 -> -1   001 * 100 = 111100 -> 1111101 -> 1111 = -1
+ 1 * -0.75 = -0.75 -> -1   001 * 101 = 111101 -> 1111110 -> 1111 = -1
+ 1 * -0.50 = -0.50 -> -1   001 * 110 = 111110 -> 1111111 -> 1111 = -1
+ 1 * -0.25 = -0.25 ->  0   001 * 111 = 111111 -> 0000000 -> 0000 =  0
+ 1 *  0.00 =  0.00 ->  0   001 * 000 = 000001 -> 0000010 -> 0000 =  0
+ 1 *  0.25 =  0.25 ->  0   001 * 001 = 000010 -> 0000011 -> 0000 =  0
+ 1 *  0.50 =  0.50 ->  1   001 * 010 = 000011 -> 0000100 -> 0001 =  1
+ 1 *  0.75 =  0.75 ->  1   001 * 011 = 000100 -> 0000101 -> 0001 =  1
+------------------------   ------------------------------------------
+ 2 * -1.00 = -2.00 -> -2   010 * 100 = 111000 -> 1111001 -> 1110 = -2
+ 2 * -0.75 = -1.50 -> -2   010 * 101 = 111010 -> 1111011 -> 1110 = -2
+ 2 * -0.50 = -1.00 -> -1   010 * 110 = 111100 -> 1111101 -> 1111 = -1
+ 2 * -0.25 = -0.50 -> -1   010 * 111 = 111110 -> 1111111 -> 1111 = -1
+ 2 *  0.00 =  0.00 ->  0   010 * 000 = 000001 -> 0000010 -> 0000 =  0
+ 2 *  0.25 =  0.50 ->  1   010 * 001 = 000011 -> 0000100 -> 0001 =  1
+ 2 *  0.50 =  1.00 ->  1   010 * 010 = 000101 -> 0000110 -> 0001 =  1
+ 2 *  0.75 =  1.50 ->  2   010 * 011 = 000111 -> 0001000 -> 0010 =  2
+------------------------   ------------------------------------------
+ 3 * -1.00 = -3.00 -> -3   011 * 100 = 110100 -> 1110101 -> 1101 = -3
+ 3 * -0.75 = -2.25 -> -2   011 * 101 = 110111 -> 1111000 -> 1110 = -2
+ 3 * -0.50 = -1.50 -> -2   011 * 110 = 111010 -> 1111011 -> 1110 = -2
+ 3 * -0.25 = -0.75 -> -1   011 * 111 = 111101 -> 1111110 -> 1111 = -1
+ 3 *  0.00 =  0.00 ->  0   011 * 000 = 000001 -> 0000010 -> 0000 =  0
+ 3 *  0.25 =  0.75 ->  1   011 * 001 = 000100 -> 0000101 -> 0001 =  1
+ 3 *  0.50 =  1.50 ->  2   011 * 010 = 000111 -> 0001000 -> 0010 =  2
+ 3 *  0.75 =  2.25 ->  2   011 * 011 = 001010 -> 0001011 -> 0010 =  2
+
+Didn't see any easy way to implement "Round Half to Even" on the FPGA DSP and maintain the forward paths. +
+
+Forwarded Shift Right by 17-bits +
+DSP is setup quite nicely for an 18-bit machine, obvious fast path is to use the built-in shift. +
+
+
// divide by a constant via multiply by reciprocal, or multiply by {0 to less than 1.0} 
+a=number; // up to 25-bit signed number on 7 series DSP
+b=fraction; // second argument is 18-bits signed, {0 to 131071} representing {0.0 to nearly 1.0}
+p=a*b+cin+65535;
+p=p>>17;
+
+ +
+ + +