Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

multiplying 64bit signed number by 64 bit signed number ARM

Status
Not open for further replies.

ahme0307

Member level 1
Joined
May 14, 2009
Messages
40
Helped
2
Reputation
4
Reaction score
2
Trophy points
1,288
Location
Ethiopia
Activity points
1,526
Please help! Any one knows how to multiply signed 64bit X signed 64 bit number in ARM using C or assembly ,


I input the two numbers as: long long int x,y;
 

Hello,

You can perform the long long multiply split it in various multiply,shift and add using the same old method of the 'hand made decimal multiply' using instead a decimal digit, a number of bit/2 that the max integer range that your compiler can manage.
 

Thanks i try to split the number but i cant hadle the carry bit and also , note also that the result will be 128 bit. do any one have idea on how to
How to input 64bit number using scanf
How to printf
multiply the two numbers
 

The best managment for calculation is a assembly routine.
How is your target? (ARM7 CortexM3 etc.)

It also can be done (slower) in portable C
How compiler you use? Wath is the max integer range ? (32 / 64)

You can enter the 64bit number as string and then traslate it.
Also the output value (122 bit plus sign) need to traslate to string for printf()
 

Thanks alex_r, I am using GNU ARM tool chain. I try to write the following code can you show me the error on the logic(algorithm)
first i try to separate the result in 128 bit as a3,a2,a1,a0 each 32 bit long
and the input as b(64 bit) b_low, b_hi
c(64 bit) c_low, c_hi

Code:
typedef signed long long int  int64;
typedef unsigned long long int  int64u;
long int a3=0,b_hi,c_hi,temp2=0;	

	int64u tempu;
	unsigned long a2=0,a1=0,a0=0,b_lo=89,c_lo=89;
	int64  temp,tempt;
	tempu=(b_lo)*(c_lo);// b_lo*c_lo
	a0=tempu;
	a1=tempu<<32;
	unsigned long int t=tempu;
	//a0=64*64;
temp=(b_lo)*(c_hi); //b_lo*c_hi
	a1=(a1)+(temp); //res a3,a2,a1,a0  a1+temp_lo
	a2=a2+temp<<32; //a2=temp_hi
temp=(b_hi)*(c_lo);//b_hi *c_lo
	a3=a3+temp<<32; //a2=a2+temp_hi
	a1=a1+temp; //a1=a1+temp_lo
	temp2=a2;//b_low=a2;
	a2=a2+a3;//a2=a2+a3
	a3=temp2+a3;//a3=b_low+a3
temp=(b_hi)*(c_hi);//b_hi*c*hi
	a2=a2+temp;// a2=a2+temp_lo
	a3=temp<<32+a3;//a3=temp_hi+a3


printf ("The result is :=%lld%lld%lld%lld\n",a3,a2,a1,a0);
 
Last edited:

This code work:
Code:
/*

to avoid confusion I made here a plain calculation
using many variable. You can simplify the code.

x,y is the 2 multiplier (signed 64 bit)
after sign valuation and (if need) sign inversion
it is split into xh xl yh yl (unsigned 32 bit)
the operations performed are:
 
             xh xl  *
             yh yl  =
             -------
             xl_yl  +                       
          xh_yl     +
          xl_yh     +
       xh_yh        =
       -------------
(sign) z3 z1 z2 z0        

 */

short sign=1;

long long x=0x7fffffffffffffff;
long long y=0x7fffffffffffffff;

unsigned long long xl_yl,xh_yl,xl_yh,xh_yh;
unsigned long long xl,xh,yl,yh;
unsigned long z3,z2,z1,z0;
unsigned long long temp_sum;

if (x<0) 
{
    x=-x;
    sign =-sign;
}

if (y<0) 
{
    y=-y;
    sign =-sign;
}

xl=x & 0xffffffff;
xh=x>>32;
yl=y & 0xffffffff;
yh=y>>32;

xl_yl=xl*yl;
xh_yl=xh*yl;
xl_yh=xl*yh;
xh_yh=xh*yh;
    
z0=xl_yl & 0xffffffff;      // result 0 

temp_sum=(xl_yl>>32)+(xh_yl & 0xffffffff)+(xl_yh & 0xffffffff);
z1=temp_sum & 0xffffffff;   // result 1

temp_sum>>=32;              // this is 'carry out' of the previous sum
temp_sum+=(xh_yl>>32)+(xl_yh>>32)+xh_yh;
z2=temp_sum & 0xffffffff;   // result 2

z3=temp_sum >>32;           // result 3

Now you have a four 32bit unsigned result plus a sign ( 1 / -1)
How to want output this number ?
 
Thank you so much alex_r, you nailed it. i want to display the number using printf, since it is not allowed to print the whole 128 bit
i am thinking to output like

Code:
printf ("The result is :=%lld%lld%lld%lld\n",z3,z2,z1,z0);

do you think there is another way?
 

You can output only the lower 64bit with printf (z1<<32) | z0 as long long
If you need a text output then you can:
-Use hexadecimal output
-Convert the result in ascii and output as string
 

alex_r

i came up with
Code:
sprintf(str,"%llx%llx%llx%llx",z3,z2,z1,z0);
printf ("The result of multiplication is=%s\n",str);
but the result is in hexadecimal i need it decimal
 

Ok. Have you a lot of billion of $ to count ? :-D

Apply a classic hex to BCD conversion algorithm and then unpack the BCD in ascii.
 
Last edited:

Thanks alex_r ,
may be i will figure out something around,
Thanks again
 

Search on edaboard for hex to bcd thread. If it isn't helpfull for you I can written the code (tomorrow)
enjoi.
 

Thank you alex_r you have done the most part. i will takecare of HEX to BCD.
Have a nice weekend!
 

Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top