diff options
Diffstat (limited to 'newlib/libc/machine/arm')
-rw-r--r-- | newlib/libc/machine/arm/Makefile.am | 2 | ||||
-rw-r--r-- | newlib/libc/machine/arm/Makefile.in | 49 | ||||
-rw-r--r-- | newlib/libc/machine/arm/access.c | 33 | ||||
-rw-r--r-- | newlib/libc/machine/arm/setjmp.S | 137 |
4 files changed, 211 insertions, 10 deletions
diff --git a/newlib/libc/machine/arm/Makefile.am b/newlib/libc/machine/arm/Makefile.am index ec5ca63e2..9d54813c6 100644 --- a/newlib/libc/machine/arm/Makefile.am +++ b/newlib/libc/machine/arm/Makefile.am @@ -6,7 +6,7 @@ INCLUDES = $(NEWLIB_CFLAGS) $(CROSS_CFLAGS) $(TARGET_CFLAGS) noinst_LIBRARIES = lib.a -lib_a_SOURCES = +lib_a_SOURCES = setjmp.S access.c ACLOCAL_AMFLAGS = -I ../../.. CONFIG_STATUS_DEPENDENCIES = $(newlib_basedir)/configure.host diff --git a/newlib/libc/machine/arm/Makefile.in b/newlib/libc/machine/arm/Makefile.in index 527ea0a9b..6e84cc057 100644 --- a/newlib/libc/machine/arm/Makefile.in +++ b/newlib/libc/machine/arm/Makefile.in @@ -89,7 +89,7 @@ INCLUDES = $(NEWLIB_CFLAGS) $(CROSS_CFLAGS) $(TARGET_CFLAGS) noinst_LIBRARIES = lib.a -lib_a_SOURCES = +lib_a_SOURCES = setjmp.S access.c ACLOCAL_AMFLAGS = -I ../../.. CONFIG_STATUS_DEPENDENCIES = $(newlib_basedir)/configure.host @@ -103,7 +103,11 @@ DEFS = @DEFS@ -I. -I$(srcdir) CPPFLAGS = @CPPFLAGS@ LIBS = @LIBS@ lib_a_LIBADD = -lib_a_OBJECTS = +lib_a_OBJECTS = setjmp.o access.o +CFLAGS = @CFLAGS@ +COMPILE = $(CC) $(DEFS) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +CCLD = $(CC) +LINK = $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(LDFLAGS) -o $@ DIST_COMMON = Makefile.am Makefile.in aclocal.m4 configure configure.in @@ -166,9 +170,35 @@ lib.a: $(lib_a_OBJECTS) $(lib_a_DEPENDENCIES) -rm -f lib.a $(AR) cru lib.a $(lib_a_OBJECTS) $(lib_a_LIBADD) $(RANLIB) lib.a + tags: TAGS -TAGS: +ID: $(HEADERS) $(SOURCES) $(LISP) + list='$(SOURCES) $(HEADERS)'; \ + unique=`for i in $$list; do echo $$i; done | \ + awk ' { files[$$0] = 1; } \ + END { for (i in files) print i; }'`; \ + here=`pwd` && cd $(srcdir) \ + && mkid -f$$here/ID $$unique $(LISP) + +TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) $(LISP) + tags=; \ + here=`pwd`; \ + list='$(SOURCES) $(HEADERS)'; \ + unique=`for i in $$list; do echo $$i; done | \ + awk ' { files[$$0] = 1; } \ + END { for (i in files) print i; }'`; \ + test -z "$(ETAGS_ARGS)$$unique$(LISP)$$tags" \ + || (cd $(srcdir) && etags $(ETAGS_ARGS) $$tags $$unique $(LISP) -o $$here/TAGS) + +mostlyclean-tags: + +clean-tags: + +distclean-tags: + -rm -f TAGS ID + +maintainer-clean-tags: distdir = $(PACKAGE)-$(VERSION) top_distdir = $(distdir) @@ -256,24 +286,24 @@ distclean-generic: maintainer-clean-generic: mostlyclean-am: mostlyclean-noinstLIBRARIES mostlyclean-compile \ - mostlyclean-generic + mostlyclean-tags mostlyclean-generic mostlyclean: mostlyclean-am -clean-am: clean-noinstLIBRARIES clean-compile clean-generic \ +clean-am: clean-noinstLIBRARIES clean-compile clean-tags clean-generic \ mostlyclean-am clean: clean-am distclean-am: distclean-noinstLIBRARIES distclean-compile \ - distclean-generic clean-am + distclean-tags distclean-generic clean-am distclean: distclean-am -rm -f config.status maintainer-clean-am: maintainer-clean-noinstLIBRARIES \ - maintainer-clean-compile maintainer-clean-generic \ - distclean-am + maintainer-clean-compile maintainer-clean-tags \ + maintainer-clean-generic distclean-am @echo "This command is intended for maintainers to use;" @echo "it deletes files that may require special tools to rebuild." @@ -283,7 +313,8 @@ maintainer-clean: maintainer-clean-am .PHONY: mostlyclean-noinstLIBRARIES distclean-noinstLIBRARIES \ clean-noinstLIBRARIES maintainer-clean-noinstLIBRARIES \ mostlyclean-compile distclean-compile clean-compile \ -maintainer-clean-compile tags distdir info-am info dvi-am dvi check \ +maintainer-clean-compile tags mostlyclean-tags distclean-tags \ +clean-tags maintainer-clean-tags distdir info-am info dvi-am dvi check \ check-am installcheck-am installcheck install-info-am install-info \ install-exec-am install-exec install-data-am install-data install-am \ install uninstall-am uninstall all-redirect all-am all installdirs \ diff --git a/newlib/libc/machine/arm/access.c b/newlib/libc/machine/arm/access.c new file mode 100644 index 000000000..8e08b3a7f --- /dev/null +++ b/newlib/libc/machine/arm/access.c @@ -0,0 +1,33 @@ +/* This is file ACCESS.C */ +/* + * Copyright (C) 1993 DJ Delorie + * All rights reserved. + * + * Redistribution and use in source and binary forms is permitted + * provided that the above copyright notice and following paragraph are + * duplicated in all such forms. + * + * This file is distributed WITHOUT ANY WARRANTY; without even the implied + * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + */ + +#include <fcntl.h> +#include <sys/stat.h> +#include <unistd.h> + +int access(const char *fn, int flags) +{ + struct stat s; + if (stat(fn, &s)) + return -1; + if (s.st_mode & S_IFDIR) + return 0; + if (flags & W_OK) + { + if (s.st_mode & S_IWRITE) + return 0; + return -1; + } + return 0; +} + diff --git a/newlib/libc/machine/arm/setjmp.S b/newlib/libc/machine/arm/setjmp.S new file mode 100644 index 000000000..d37486090 --- /dev/null +++ b/newlib/libc/machine/arm/setjmp.S @@ -0,0 +1,137 @@ +/* This is a simple version of setjmp and longjmp. + + Nick Clifton, Cygnus Solutions, 13 June 1997. */ + +/* ANSI concatenation macros. */ +#define CONCAT(a, b) CONCAT2(a, b) +#define CONCAT2(a, b) a##b + +#ifndef __USER_LABEL_PREFIX__ +#error __USER_LABEL_PREFIX__ not defined +#endif + +#define SYM(x) CONCAT (__USER_LABEL_PREFIX__, x) + +#ifdef __ELF__ +#define TYPE(x) .type SYM(x),function +#define SIZE(x) .size SYM(x), . - SYM(x) +#else +#define TYPE(x) +#define SIZE(x) +#endif + +/* Arm/Thumb interworking support: + + The interworking scheme expects functions to use a BX instruction + to return control to their parent. Since we need this code to work + in both interworked and non-interworked environments as well as with + older processors which do not have the BX instruction we do the + following: + Test the return address. + If the bottom bit is clear perform an "old style" function exit. + (We know that we are in ARM mode and returning to an ARM mode caller). + Otherwise use the BX instruction to perform the function exit. + + We know that we will never attempt to perform the BX instruction on + an older processor, because that kind of processor will never be + interworked, and a return address with the bottom bit set will never + be generated. + + In addition, we do not actually assemble the BX instruction as this would + require us to tell the assembler that the processor is an ARM7TDMI and + it would store this information in the binary. We want this binary to be + able to be linked with binaries compiled for older processors however, so + we do not want such information stored there. + + If we are running using the APCS-26 convention however, then we never + test the bottom bit, because this is part of the processor status. + Instead we just do a normal return, since we know that we cannot be + returning to a Thumb caller - the Thumb does not support APCS-26. + + Function entry is much simpler. If we are compiling for the Thumb we + just switch into ARM mode and then drop through into the rest of the + function. The function exit code will take care of the restore to + Thumb mode. */ + +#ifdef __APCS_26__ +#define RET movs pc, lr +#else +#define RET tst lr, #1; \ + moveq pc, lr ; \ +.word 0xe12fff1e /* bx lr */ +#endif + +#ifdef __thumb__ +#define MODE .thumb_func +.macro PROLOGUE name + .code 16 + bx pc + nop + .code 32 +SYM (.arm_start_of.\name): +.endm +#else +#define MODE .code 32 +.macro PROLOGUE name +.endm +#endif + +.macro FUNC_START name + .text + .align 2 + MODE + .globl SYM (\name) + TYPE (\name) +SYM (\name): + PROLOGUE \name +.endm + +.macro FUNC_END name + RET + SIZE (\name) +.endm + +/* -------------------------------------------------------------------- + int setjmp (jmp_buf); + -------------------------------------------------------------------- */ + + FUNC_START setjmp + + /* Save all the callee-preserved registers into the jump buffer. */ + stmea a1!, { v1-v7, fp, ip, sp, lr } + +#if 0 /* Simulator does not cope with FP instructions yet. */ +#ifndef __SOFTFP__ + /* Save the floating point registers. */ + sfmea f4, 4, [a1] +#endif +#endif + /* When setting up the jump buffer return 0. */ + mov a1, #0 + + FUNC_END setjmp + +/* -------------------------------------------------------------------- + volatile void longjmp (jmp_buf, int); + -------------------------------------------------------------------- */ + + FUNC_START longjmp + + /* If we have stack extension code it ought to be handled here. */ + + /* Restore the registers, retrieving the state when setjmp() was called. */ + ldmfd a1!, { v1-v7, fp, ip, sp, lr } + +#if 0 /* Simulator does not cope with FP instructions yet. */ +#ifndef __SOFTFP__ + /* Restore floating point registers as well. */ + lfmfd f4, 4, [a1] +#endif +#endif + /* Put the return value into the integer result register. + But if it is zero then return 1 instead. */ + movs a1, a2 + moveq a1, #1 + + FUNC_END longjmp + |