Update.
authorUlrich Drepper <drepper@redhat.com>
Wed, 1 Apr 1998 09:15:07 +0000 (09:15 +0000)
committerUlrich Drepper <drepper@redhat.com>
Wed, 1 Apr 1998 09:15:07 +0000 (09:15 +0000)
1998-04-1 16:52  Philip Blundell  <pb@nexus.co.uk>

* sysdeps/unix/sysv/linux/arm/socket.S: Correct test for error and
use PLTJMP() rather than explicit (PLT).

* sysdeps/arm/elf/start.S: Leave most of the initialisation for
__libc_start_main().

Based on patch from Pat Beirne:
* sysdeps/unix/sysv/linux/arm/sysdep.h (SYSCALL_ERROR_HANDLER):
Always define, not only #ifndef PIC.
(DO_CALL): Pass fifth argument correctly in R4.
(PSEUDO): Correct test for error, call syscall_error through PLT
if PIC.

1998-03-31 10:51  Philip Blundell  <pb@nexus.co.uk>

* sysdeps/unix/sysv/linux/netash/ash.h: Fix typos and add new
definitions.

ChangeLog
sysdeps/arm/elf/start.S
sysdeps/unix/sysv/linux/arm/socket.S
sysdeps/unix/sysv/linux/arm/sysdep.h
sysdeps/unix/sysv/linux/netash/ash.h

index fec9c38..ff25cfe 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,23 @@
+1998-04-1 16:52  Philip Blundell  <pb@nexus.co.uk>
+
+       * sysdeps/unix/sysv/linux/arm/socket.S: Correct test for error and
+       use PLTJMP() rather than explicit (PLT).
+
+       * sysdeps/arm/elf/start.S: Leave most of the initialisation for
+       __libc_start_main().
+
+       Based on patch from Pat Beirne:
+       * sysdeps/unix/sysv/linux/arm/sysdep.h (SYSCALL_ERROR_HANDLER):
+       Always define, not only #ifndef PIC.
+       (DO_CALL): Pass fifth argument correctly in R4.
+       (PSEUDO): Correct test for error, call syscall_error through PLT
+       if PIC.
+
+1998-03-31 10:51  Philip Blundell  <pb@nexus.co.uk>
+
+       * sysdeps/unix/sysv/linux/netash/ash.h: Fix typos and add new
+       definitions.
+
 1998-04-01  Ulrich Drepper  <drepper@cygnus.com>
 
        * iconvdata/Makefile: Remove extra dependencies for EUC-KR.so and
index e0964a1..13b9c78 100644 (file)
        This includes _init and _libc_init
 
 
-       At this entry point, most registers' values are unspecified, except for:
+       At this entry point, most registers' values are unspecified, except:
 
-   r0          Contains a function pointer to be registered with `atexit'.
+   a1          Contains a function pointer to be registered with `atexit'.
                This is how the dynamic linker arranges to have DT_FINI
                functions called for shared libraries that have been loaded
                before this code runs.
 
    sp          The stack contains the arguments and environment:
-               0(%esp)                 argc
-               4(%esp)                 argv[0]
+               0(sp)                   argc
+               4(sp)                   argv[0]
                ...
-               (4*argc)(%esp)          NULL
-               (4*(argc+1))(%esp)      envp[0]
+               (4*argc)(sp)            NULL
+               (4*(argc+1))(sp)        envp[0]
                ...
                                        NULL
 */
        .text
        .globl _start
 _start:
-       /* Clear the frame pointer.  The Intel ABI suggests this be done,
-               to mark the outermost frame obviously. This seems like a
-               sensible thing to do  */
+       /* Clear the frame pointer since this is the outermost frame.  */
        mov fp, #0
 
-       /* r0 contains the address of the shared library termination
-          function, which we will register with `atexit' to be called by
-          `exit'.  I suspect that on some systems, and when statically
-          linked, this will not be set by anything to any function
-          pointer; hopefully it will be zero so we don't try to call
-          random pointers.  */
-       cmp r0,#0
-       blne atexit(PLT)
-
-       /* Do essential libc initialization.  In statically linked
-          programs under the GNU Hurd, this is what sets up the
-          arguments on the stack for the code below. For dyn-link
-          programs, this has been run already, in the .init code. */
-#ifndef PIC
-       bl __libc_init_first
-
-       /* Extract the arguments and environment as encoded on the stack
-          and set up the arguments for `main': argc, argv, envp.  */
-       ldr r0,[sp]
-       add r1,sp,#4
-       add r2,r1,r0,lsl #2
-       add r2,r2,#4
-       /* save a copy of envp while we have it */
-       ldr r3,L_environ
-       str r2,[r3]
-
-       /* Call `_init', which is the entry point to our own `.init'
-          section; and register with `atexit' to have `exit' call
-          `_fini', which is the entry point to our own `.fini' section.  */
-       bl _init
-       ldr r0,L_fini
-       bl atexit
-       b L_pfini
-
-L_fini:        .word _fini
-L_environ: .word _environ
-L_pfini:
-#endif
-       /* rebuild the arg list for main() */
-       ldr r0,[sp]
-       add r1,sp,#4
-       add r2,r1,r0,lsl #2
-       add r2,r2,#4
-
-       /* Call the user's main function, and exit with its value.  */
-       bl main
-       bl exit
+       /* Pop argc off the stack and save a pointer to argv */
+       ldmfd sp!, {a2}
+       mov a3, sp
+
+       /* Push the last arguments to main() onto the stack */
+       stmfd sp!, {a1}
+       ldr a1, =_fini
+       stmfd sp!, {a1}
+
+       /* Set up the other arguments for main() that go in registers */
+       ldr a1, =main
+       ldr a4, =_init
+
+       /* __libc_start_main (main, argc, argv, init, fini, rtld_fini) */
+
+       /* Let the libc call main and exit with its return code.  */
+       bl __libc_start_main
        /* should never get here....*/
        bl abort
 
-
 /* Define a symbol for the first piece of initialized data.  */
        .data
        .globl __data_start
index 0ff6dd0..1ebec9c 100644 (file)
@@ -43,7 +43,7 @@ ENTRY (__socket)
 
        /* r0 is < 0 if there was an error.  */
        cmn r0, $124
-       bge syscall_error(PLT)
+       bhs PLTJMP(syscall_error)
 
        /* Successful; return the syscall's value.  */
        RETINSTR(mov,pc,r14)
index 3b7ffe0..dd1b6f4 100644 (file)
    is a real error number.  Linus said he will make sure the no syscall
    returns a value in -1 .. -4095 as a valid result so we can savely
    test with -4095.  */
+
 #undef PSEUDO
 #define        PSEUDO(name, syscall_name, args)                                      \
   .text;                                                                     \
+  .type syscall_error,%function                                                      \
   ENTRY (name)                                                               \
     DO_CALL (args, syscall_name);                                            \
     cmn r0, $4096;                                                           \
-    bgt syscall_error;
+    bhs PLTJMP(syscall_error);
 
 #undef PSEUDO_END
 #define        PSEUDO_END(name)                                                      \
   SYSCALL_ERROR_HANDLER                                                              \
   END (name)
 
-#ifndef PIC
 #define SYSCALL_ERROR_HANDLER  /* Nothing here; code in sysdep.S is used.  */
-#else
-#error Aiee
-#endif /* PIC */
+
+/* Linux takes system call args in registers:
+       syscall number  in the SWI instruction
+       arg 1           r0
+       arg 2           r1
+       arg 3           r2
+       arg 4           r3
+       arg 5           r4      (this is different from the APCS convention)
+
+   The compiler is going to form a call by coming here, through PSEUDO, with
+   arguments
+       syscall number  in the DO_CALL macro
+       arg 1           r0
+       arg 2           r1
+       arg 3           r2
+       arg 4           r3
+       arg 5           [sp]
+
+   We need to shuffle values between R4 and the stack so that the caller's
+   R4 is not corrupted, and the kernel sees the right argument there.
+
+*/
 
 #undef DO_CALL
-#define DO_CALL(args, syscall_name)                                          \
-    swi SYS_ify (syscall_name);
+#define DO_CALL(args, syscall_name)            \
+    DOARGS_##args                              \
+    swi SYS_ify (syscall_name);                \
+    UNDOARGS_##args
+
+#define DOARGS_0 /* nothing */
+#define DOARGS_1 /* nothing */
+#define DOARGS_2 /* nothing */
+#define DOARGS_3 /* nothing */
+#define DOARGS_4 /* nothing */
+#define DOARGS_5 ldr ip, [sp]; str r4, [sp]; mov r4, ip;
+
+#define UNDOARGS_0 /* nothing */
+#define UNDOARGS_1 /* nothing */
+#define UNDOARGS_2 /* nothing */
+#define UNDOARGS_3 /* nothing */
+#define UNDOARGS_4 /* nothing */
+#define UNDOARGS_5 ldr r4, [sp];
 
 #endif /* ASSEMBLER */
 
index e4feec4..52bd398 100644 (file)
    write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
    Boston, MA 02111-1307, USA.  */
 
-#ifndef __NETASH_ASH_H
-#define __NETASH_ASH_H 1
+#ifndef _NETASH_ASH_H
+#define _NETASH_ASH_H  1
 
 #include <features.h>
-#include <sys/socket.h>
-#include <sys/types.h>
+#include <bits/sockaddr.h>
 
 struct sockaddr_ash
   {
-    _SOCKADDR_COMMON (sash_);          /* Common data: address family etc.  */
-    int if_index;                      /* Interface to use.  */
-    int channel;                       /* Realtime or control.  */
+    __SOCKADDR_COMMON (sash_);         /* Common data: address family etc.  */
+    int sash_ifindex;                  /* Interface to use.  */
+    unsigned char sash_channel;                /* Realtime or control.  */
+    unsigned int sash_plen;
+    unsigned char sash_prefix[16];
   };
 
+/* Values for `channel' member.  */
+#define ASH_CHANNEL_ANY                0
+#define ASH_CHANNEL_CONTROL    1
+#define ASH_CHANNEL_REALTIME   2
+
 #endif /* netash/ash.h */