## Main :: ToneCore Development Kit

**integer multiplication - stupid assembly question**

by audioartillery on 2010-02-06 12:43:59

Using the standard mpy instruction works great for fixed-point multiplication. But for regular integer multiplication (e.g., 5*4 = 20) you can't just do this:

move #$5,x0

move #$4,x1

mpy x0,x1,b

Because $000005 and $000004 are really small fractions. You end up getting 0 in b. Is there an equivalent integer multiplication instruction? I haven't found one. Performing the multiplication by a loop of additions is really, really slow.

Edit: ok, I'm confused. The below actually results in the value 0x001e00.

move #$5,x0

move #$3,x1

mpy x0,x1,b

What is going on here? If I take 0x001e00 and shift it down 9 bits I get the answer I'm looking for. Also, $5 comes out as 0x050000 in the GUI. I'm not sure how I got this far without understanding the multiplication (I've got a semi-complicated effect sorta-working).

**Re: integer multiplication - stupid assembly question**

by RedPandaCurt on 2010-02-06 18:37:43

Think of the integers being scaled by some factor so that all numbers lie in the range [-1,+1). The scaling factor is a tradeoff between magnitude and precision. If the maximum possible value is 20 you could use 1/32 as the scaling factor, but I will use 1/128 in this example so that it is easier to see in the ToneCore UI hex display (not 1/256 - one bit is the sign bit). You need to rescale the multiplication results, which can be done using arithmetic shifts if the scaling factor is a power of 2.

Integer: 5 * 4 = 20

Fixed point: 5/128 *4/128 = 20/16384

multiply by 128 to get 20/128, which is the number you are looking for.

Here is some code:

move #>$050000,x0

move #>$040000,x1

mpy x0,x1,b

asl #7,b,b

move b,x:Debug_Read_from_DSP_4 ; displays 140000

**Re: integer multiplication - stupid assembly question**

by audioartillery on 2010-02-06 20:54:10

Thanks, RedPanda. It makes sense, I was just hoping for something more automatic. The accumulator shifter part of the processor is somewhat configurable from my read of the 56300 family manual, but I didn't see any option or instruction to prevent it from shifting.

For the data I need to handle I need to spend some time analyzing my algorithm to determine out the right precision to use, but it will work. I guess I could dynamically choose the precision based on the data, but that could burn a lot of cycles.

The information above may not be current, and you should direct questions to the current forum or review the manual.