On Thu, Jan 10, 2002 at 11:53:44PM -0500, Lam Yick Yan wrote:
>      I am a C programmer, and now I got a task to write assembly
> language (in Linux enviroment) for some time crucial function....
> 
>      I am not very familiar with gcc. I have written
> the following very simple function, it compiles successfully. However
> when I run it, I got segmentation fault....
> 

[snip]

> The mul fuction is written in Assembly (mul.S) as follow:
> (not finished Yet, just simple function doing nothing)
> ----------------------------------------------------------------------
>      .text
>      .align
> 
>      .global mul
>      .global _mul
> 
> mul:
> _mul:
>      stmdb sp!, {r4-r12, lr}   @ push everything onto the stack...
>      adr  r0, Rm_backup
>      str  r1, [r0]
>      ldmia sp!, {r4-r12, pc}   @ return with <lr> destroyed

This is slow. You first push everything on the stack, then do the
actual computation and then then restore everything again. It's *much*
faster to use inline assembly in this case, especially if the
computation is indeed simple. There are two excellent inline assembly
links on the kernelnewbies links page, see:

  http://www.kernelnewbies.org/links/

and look for "assembly". The links are about x86 assembly, but it also
applies to arm assembly.

> The Makefile is
> ---------------------------------------------------------------------------
> CC=arm-linux-gcc
> CFLAGS= -Wall -O  \
>          -fforce-mem -fforce-addr -fthread-jumps -fcse-follow-jumps \
>                  -fcse-skip-blocks -fexpensive-optimizations -fregmove\
>                  -fschedule-insns2 -fstrength-reduce -finline-functions\
>                  -fomit-frame-pointer

Ehm, don't do that, not all combinations of compiler flag are valid.
You'd better use -O2 or -Os combined with -fomit-frame-pointer and the
correct architecture parameters (-march=armv4 -mtune=strongarm1100 for
SA11x0 systems).

> all: main
> 
> main: mul.o main.o
>          $(CC) $(CFLAGS) -o main mul.o main.o
> 
> main.o: main.c
>          $(CC) $(CFLAGS) -c main.c -o main.o

Let me introduce you to implicit makefile rules. This implicit rule
will tell make how to make .o files from .c files:

.c.o:
        $(CC) $(CFLAGS) -c $< -o $@

> mul.o: mul.S
>          $(CC) $(CFLAGS) -c mul.S -o mul.o

Same for .S files:

.S.o:
        $(CC) $(CFLAGS) -c $< -o $@


>      The intention in mul.S is to declare 3 local variables,
> Rm_backup, Rs_backup and ip_backup and store value of r1 into it
> but when I run, I got segmentatin fault immediately. Why???

Let the program dump core (limit coredumpsize unlimited in tcsh, ulimit
-c unlimited in bash), run it through a debugger (gdb main core) to
get a backtrace (bt) and you'll see exactly why it went wrong.

>      Another question: can someone tell me how can I implement the 
> following C functions in ARM assembly language:
> 
> 1) long mul(long a, long b, long *c, long *d) {
>         long e=3;
> 
>         *c=a+e;
>         *d=*c;
>         return *d;
>      }

Try "arm-linux-gcc -g -O2 -c foo.c -o foo.o", run "arm-linux-objdump -D
-S foo.o | less" and you'll see how to do it.


Erik

-- 
J.A.K. (Erik) Mouw, Information and Communication Theory Group, Faculty
of Information Technology and Systems, Delft University of Technology,
PO BOX 5031, 2600 GA Delft, The Netherlands  Phone: +31-15-2783635
Fax: +31-15-2781843  Email: [EMAIL PROTECTED]
WWW: http://www-ict.its.tudelft.nl/~erik/

_______________________________________________
http://lists.arm.linux.org.uk/mailman/listinfo/linux-arm
Please visit the above address for information on this list.

Reply via email to