diff --git a/libgloss/ChangeLog b/libgloss/ChangeLog index 0f236a7e7..b1293fb4e 100644 --- a/libgloss/ChangeLog +++ b/libgloss/ChangeLog @@ -1,3 +1,21 @@ +2014-12-15 Nick Hung + + * libgloss/nds32/_exit.S: Finish with an infinite loop in _exit. + * libgloss/nds32/_getpid.S: Don't issue _getpid system call, it is + always successful. + * libgloss/nds32/_gettimeofday.S: No error for _gettimeofday is defined + in SYS_geterr handler. + * libgloss/nds32/_isatty.S: No error for _isatty is defined in + SYS_geterr handler. + * libgloss/nds32/_kill.S: Alway fail. errno = EINVAL. + * libgloss/nds32/_link.S: Alway fail. errno = EMLINK. + * libgloss/nds32/_times.S: Alway fail. errno = EACCES. + * libgloss/nds32/_unlink.S: fix copy and paste error. + * libgloss/nds32/crt0.S: Add pre_c_init, post_c_init, arg_init. + * libgloss/nds32/crt1.S: Add pre_c_init, post_c_init, arg_init. + * libgloss/nds32/syscall_extra.h: Re-format. + * libgloss/nds32/vh.h: Add more virtual hosting number. + 2014-12-11 Anthony Green * moxie/configure: Rebuilt. diff --git a/libgloss/nds32/_exit.S b/libgloss/nds32/_exit.S index 8154fbed5..1a73fa20a 100644 --- a/libgloss/nds32/_exit.S +++ b/libgloss/nds32/_exit.S @@ -27,22 +27,18 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#ifdef __NDS32_VH__ - #include "vh.h" -.extern _impure_ptr -TYPE3 _exit, VH_EXIT - -#else /* not __NDS32_VH__ */ - #include "../syscall.h" -#include "syscall_extra.h" - .section .text + .text .global _exit .type _exit, @function - .align 2 + .align 2 _exit: +#ifdef __NDS32_VH__ + BREAK VH_EXIT /* Generate_Exception(Breakpoint); */ +#else syscall SYS_exit /* Make syscall 'SYS_exit'. */ +#endif +.L_infinite_loop: + b .L_infinite_loop .size _exit, .-_exit - -#endif /* not __NDS32_VH__ */ diff --git a/libgloss/nds32/_getpid.S b/libgloss/nds32/_getpid.S index 086be8461..c8662d20d 100644 --- a/libgloss/nds32/_getpid.S +++ b/libgloss/nds32/_getpid.S @@ -28,10 +28,13 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#ifndef __NDS32_VH__ - -#include "../syscall.h" -#include "syscall_extra.h" -SYS_WRAPPER _getpid, SYS_getpid - -#endif /* not __NDS32_VH__ */ + .text + .global _getpid + .type _getpid, @function + .align 2 +_getpid: + /* The getpid() function shall always be successful and + no return value is reserved to indicate an error. */ + movi $r0, 1 /* A minimal implementation, success. */ + ret + .size _getpid, .-_getpid diff --git a/libgloss/nds32/_gettimeofday.S b/libgloss/nds32/_gettimeofday.S index adc5f6847..e78bd5e19 100644 --- a/libgloss/nds32/_gettimeofday.S +++ b/libgloss/nds32/_gettimeofday.S @@ -30,13 +30,19 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. #ifdef __NDS32_VH__ #include "vh.h" -.extern _impure_ptr TYPE3 _gettimeofday, VH_GETTIMEOFDAY #else /* not __NDS32_VH__ */ #include "../syscall.h" #include "syscall_extra.h" -SYS_WRAPPER _gettimeofday, SYS_gettimeofday + .text + .global _gettimeofday + .type _gettimeofday, @function + .align 2 +_gettimeofday: + syscall SYS_gettimeofday + ret + .size _gettimeofday, .-_gettimeofday #endif /* not __NDS32_VH__ */ diff --git a/libgloss/nds32/_isatty.S b/libgloss/nds32/_isatty.S index c90028afc..37776ed7d 100644 --- a/libgloss/nds32/_isatty.S +++ b/libgloss/nds32/_isatty.S @@ -27,6 +27,15 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +/* + SYNOPSIS + #include + int isatty(int fildes); + RETURN VALUE + The isatty() function shall return 1 if fildes is associated with + a terminal; otherwise, it shall return 0 and may set errno + to indicate the error. +*/ #ifdef __NDS32_VH__ #include "vh.h" @@ -37,6 +46,21 @@ TYPE0 _isatty, VH_ISATTY #include "../syscall.h" #include "syscall_extra.h" -SYS_WRAPPER _isatty, SYS_isatty + .text + .global _isatty + .type _isatty, @function + .align 2 +_isatty: + syscall SYS_isatty /* Make syscall with SWID=`SYS_isatty'. + Reture value `0' stored in $r0 means + there is something wrong. */ + bnez $r0, 1f /* Branch if success. */ + syscall SYS_geterr /* There is something wrong. */ + l.w $r15, _impure_ptr + swi $r0, [$r15] /* Set errno. */ + move $r0, #0 +1: + ret + .size _isatty, .-_isatty #endif /* not __NDS32_VH__ */ diff --git a/libgloss/nds32/_kill.S b/libgloss/nds32/_kill.S index 69d8b41c6..bb8c6ebd3 100644 --- a/libgloss/nds32/_kill.S +++ b/libgloss/nds32/_kill.S @@ -27,11 +27,20 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ - -#ifndef __NDS32_VH__ - -#include "../syscall.h" -#include "syscall_extra.h" -SYS_WRAPPER _kill, SYS_kill - -#endif /* not __NDS32_VH__ */ +/* Upon successful completion, 0 shall be returned. Otherwise, + -1 shall be returned and errno set to indicate the error. */ + .extern _impure_ptr /* The first element is _errno. */ + .text + .global _kill + .type _kill, @function + .align 2 +_kill: + /* A minimal implementation has no concept of either signals, + nor of processes to receive those signals. So this function + should always fail with an appropriate value in errno. */ + movi $r0, #22 /* EINVAL: Invalid argument */ + l.w $r15, _impure_ptr + swi $r0, [$r15] + movi $r0, -1 /* Set return value to -1. */ + ret + .size _kill, .-_kill diff --git a/libgloss/nds32/_link.S b/libgloss/nds32/_link.S index 15016fcc1..7f6b7f0fa 100644 --- a/libgloss/nds32/_link.S +++ b/libgloss/nds32/_link.S @@ -27,10 +27,19 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#ifndef __NDS32_VH__ - -#include "../syscall.h" -#include "syscall_extra.h" -SYS_WRAPPER _link, SYS_link - -#endif /* not __NDS32_VH__ */ +/* Upon successful completion, 0 shall be returned. Otherwise, + -1 shall be returned and errno set to indicate the error. */ + .extern _impure_ptr /* The first element is _errno. */ + .text + .global _link + .type _link, @function + .align 2 +_link: + /* A minimal implementation has no file system, so this function + must always fail, with an appropriate value set in errno. */ + movi $r0, #31 /* EMLINK: Too many links */ + l.w $r15, _impure_ptr + swi $r0, [$r15] + movi $r0, -1 /* Set return value to -1. */ + ret + .size _link, .-_link diff --git a/libgloss/nds32/_times.S b/libgloss/nds32/_times.S index 048de6208..3343f315b 100644 --- a/libgloss/nds32/_times.S +++ b/libgloss/nds32/_times.S @@ -27,10 +27,19 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#ifndef __NDS32_VH__ - -#include "../syscall.h" -#include "syscall_extra.h" -SYS_WRAPPER _times, SYS_times - -#endif /* not __NDS32_VH__ */ +/* If times() fails, (clock_t)-1 shall be returned and errno set + to indicate the error. */ + .extern _impure_ptr /* The first element is _errno. */ + .text + .global _times + .type _times, @function + .align 2 +_times: + /* A minimal implementation need not offer any timing information, + so should always fail with an appropriate value in errno. */ + movi $r0, #13 /* EACCES: Permission denied */ + l.w $r15, _impure_ptr + swi $r0, [$r15] + movi $r0, -1 /* Set return value to -1. */ + ret + .size _times, .-_times diff --git a/libgloss/nds32/_unlink.S b/libgloss/nds32/_unlink.S index ec251b504..bb5989c3f 100644 --- a/libgloss/nds32/_unlink.S +++ b/libgloss/nds32/_unlink.S @@ -32,7 +32,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. #include "vh.h" .extern _impure_ptr -TYPE1 _lseek, VH_LSEEK +TYPE1 _unlink, VH_UNLINK #else /* not __NDS32_VH__ */ diff --git a/libgloss/nds32/crt0.S b/libgloss/nds32/crt0.S index 968b7352b..68a6f76d4 100644 --- a/libgloss/nds32/crt0.S +++ b/libgloss/nds32/crt0.S @@ -36,6 +36,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ## ##============================================================================== +#include "syscall_extra.h" + ##------------------------------------------------------------------------------ ## Vector table setup ##------------------------------------------------------------------------------ @@ -47,6 +49,11 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ##------------------------------------------------------------------------------ .section .text .weak _SDA_BASE_ + .weak _ITB_BASE_ + .weak _arg_init + .weak __pre_c_init + .weak __post_c_init + .weak _call_exit .global _start .type _start, @function .align 2 @@ -60,8 +67,22 @@ _start: determined by Linker. SDA stands for Small Data Access. */ la $gp, _SDA_BASE_ +#if __NDS32_EXT_EX9__ +.L_init_itb: + /* Initialization for Instruction Table Base (ITB). + The symbol _ITB_BASE_ is determined by Linker. + Set $ITB only if MSC_CFG.EIT (cr4.b'24) is set. */ + mfsr $r0, $MSC_CFG + srli $r0, $r0, 24 + andi $r0, $r0, 0x1 + beqz $r0, 1f /* Fall through ? */ + la $r0, _ITB_BASE_ + mtusr $r0, $ITB +1: +#endif + .L_init_sp: - /* Initialization for stack pointe. The symbol _stack is defined + /* Initialization for stack pointer. The symbol _stack is defined in linker script. Make sure $sp is 8-byte aligned. */ la $sp, _stack #if __NDS32_ISA_V3__ @@ -71,23 +92,33 @@ _start: and $sp, $sp, $r0 #endif -#if __NDS32_EX9_EXT__ -.L_init_itb: - /* Initialization for Instruction Table Base (ITB). - The symbol $_ITB_BASE_ is determined by Linker. - Set $ITB only if MSC_CFG.EIT (cr4.b'24) is set. */ - mfsr $r0, $MSC_CFG - srli $r0, $r0, 24 - andi $r0, $r0, 0x1 - beqz $r0, .L_zero_out_bss /* Fall through ? */ - la $r0, $_ITB_BASE_ - mtusr $r0, $ITB +#if __NDS32_EXT_FPU_SP__ || __NDS32_EXT_FPU_DP__ +.L_init_fpu: + /* Initialize FPU + Set FUCOP_CTL.CP0EN (fucpr.b'0). */ + mfsr $r0, $FUCOP_CTL + ori $r0, $r0, 0x1 + mtsr $r0, $FUCOP_CTL + dsb + /* According to [bugzilla #9425], set flush-to-zero mode. + That is, set $FPCSR.DNZ(b'12) = 1. */ + FMFCSR $r0 + ori $r0, $r0, 0x1000 + FMTCSR $r0 + dsb #endif +.L_pre_c_init: + ! call __pre_c_init if provided + ! sample __pre_c_init is in BSP + la $r15, __pre_c_init ! load address of __pre_c_init + beqz $r15, .L_zero_out_bss ! check existence of __pre_c_init + jral $r15 ! pre-c-runtime initialization + .L_zero_out_bss: /* Zero out the bss section. Equivalence C code for follow part: - if (_end == _edata) goto .L_call_main + if (_end == _edata) goto .L_post_c_init unsinged int *ptr = _edata; while (ptr != _end) *ptr++ = 0 @@ -98,21 +129,52 @@ _start: la $r0, _edata la $r1, _end movi $r2, #0 - beq $r0, $r1, .L_call_main /* Branch if no bss. */ + beq $r0, $r1, .L_post_c_init /* Branch if no bss. */ .Lword_clear: swi.bi $r2, [$r0], #4 bne $r0, $r1, .Lword_clear -.L_call_main: +.L_post_c_init: + ! call __post_c_init if provided + ! no sample __post_c_init is provided + la $r15, __post_c_init ! load address of __post_c_init + beqz $r15, .L_arg_init ! check existence of __post_c_init + jral $r15 ! post-c-runtime initialization + +.L_arg_init: + ! argc/argv initialization if necessary + la $r7, _arg_init ! get address of _arg_init + beqz $r7, .L_clean_reg ! if there isn't _arg_init, go main + addi $sp, $sp, -512 ! allocate space for command line + ! and arguments + move $r6, $sp ! r6 = buffer addr of cmd line + move $r0, $r6 ! r0 = buffer addr of cmd line + syscall SYS_getcmdline ! get cmd line + move $r0, $r6 ! r0 = buffer addr of cmd line + addi $r1, $r6, 256 ! r1 = argv + jral $r7 ! init argc/argv + addi $r1, $r6, 256 ! r1 = argv + b .L_call_main + +.L_clean_reg: /* Prepare argc/argv/env for main function. Since there is no operating system so far, we set $r0, $r1, and $r2 to be zero. - Note: $r2 already set to zero in line 84. */ + Note: $r2 already set to zero in .L_zero_out_bss: code fragment. */ movi $r0, 0 movi $r1, 0 + movi $r2, 0 + +.L_call_main: /* Call 'main'. */ bal main + /* Call _call_exit. */ + ! call _call_exit if necessary; default implementation is in crtexit.c + la $r15, _call_exit ! load address of _call_exit + beqz $r15, .L_terminate_program ! no _call_exit? go exit + jral $r15 ! _call_exit will never return + .L_terminate_program: /* There are two ways to terminate program: 1. User "syscall 0x1" directly. diff --git a/libgloss/nds32/crt1.S b/libgloss/nds32/crt1.S index 2ff2eea6d..ec8b86683 100644 --- a/libgloss/nds32/crt1.S +++ b/libgloss/nds32/crt1.S @@ -36,6 +36,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ## ##============================================================================== +#include "syscall_extra.h" + ##------------------------------------------------------------------------------ ## Vector table setup ##------------------------------------------------------------------------------ @@ -47,6 +49,11 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. ##------------------------------------------------------------------------------ .section .text .weak _SDA_BASE_ + .weak _ITB_BASE_ + .weak _arg_init + .weak __pre_c_init + .weak __post_c_init + .weak _call_exit .global _start .type _start, @function .align 2 @@ -60,8 +67,22 @@ _start: determined by Linker. SDA stands for Small Data Access. */ la $gp, _SDA_BASE_ +#if __NDS32_EXT_EX9__ +.L_init_itb: + /* Initialization for Instruction Table Base (ITB). + The symbol _ITB_BASE_ is determined by Linker. + Set $ITB only if MSC_CFG.EIT (cr4.b'24) is set. */ + mfsr $r0, $MSC_CFG + srli $r0, $r0, 24 + andi $r0, $r0, 0x1 + beqz $r0, 1f /* Fall through ? */ + la $r0, _ITB_BASE_ + mtusr $r0, $ITB +1: +#endif + .L_init_sp: - /* Initialization for stack pointe. The symbol _stack is defined + /* Initialization for stack pointer. The symbol _stack is defined in linker script. Make sure $sp is 8-byte aligned. */ la $sp, _stack #if __NDS32_ISA_V3__ @@ -71,19 +92,29 @@ _start: and $sp, $sp, $r0 #endif -#if __NDS32_EX9_EXT__ -.L_init_itb: - /* Initialization for Instruction Table Base (ITB). - The symbol $_ITB_BASE_ is determined by Linker. - Set $ITB only if MSC_CFG.EIT (cr4.b'24) is set. */ - mfsr $r0, $MSC_CFG - srli $r0, $r0, 24 - andi $r0, $r0, 0x1 - beqz $r0, .L_zero_out_bss /* Fall through ? */ - la $r0, $_ITB_BASE_ - mtusr $r0, $ITB +#if __NDS32_EXT_FPU_SP__ || __NDS32_EXT_FPU_DP__ +.L_init_fpu: + /* Initialize FPU + Set FUCOP_CTL.CP0EN (fucpr.b'0). */ + mfsr $r0, $FUCOP_CTL + ori $r0, $r0, 0x1 + mtsr $r0, $FUCOP_CTL + dsb + /* According to [bugzilla #9425], set flush-to-zero mode. + That is, set $FPCSR.DNZ(b'12) = 1. */ + FMFCSR $r0 + ori $r0, $r0, 0x1000 + FMTCSR $r0 + dsb #endif +.L_pre_c_init: + ! call __pre_c_init if provided + ! sample __pre_c_init is in BSP + la $r15, __pre_c_init ! load address of __pre_c_init + beqz $r15, .L_zero_out_bss ! check existence of __pre_c_init + jral $r15 ! pre-c-runtime initialization + .L_zero_out_bss: /* Zero out the bss section. Equivalence C code for follow part: @@ -97,28 +128,61 @@ _start: */ la $r0, _edata la $r1, _end - beq $r0, $r1, .L_call_main /* Branch if no bss. */ movi $r2, #0 + beq $r0, $r1, .L_cpp_init /* Branch if no bss. */ .Lword_clear: swi.bi $r2, [$r0], #4 bne $r0, $r1, .Lword_clear -.L_call_main: +.L_cpp_init: /* Call '_init' to invoke constructors. */ jal _init /* Register '_fini' into atexit() to invoke destructors when exit() has been reached. */ la $r0, _fini jal atexit + +.L_post_c_init: + ! call __post_c_init if provided + ! no sample __post_c_init is provided + la $r15, __post_c_init ! load address of __post_c_init + beqz $r15, .L_arg_init ! check existence of __post_c_init + jral $r15 ! post-c-runtime initialization + +.L_arg_init: + ! argc/argv initialization if necessary + la $r7, _arg_init ! get address of _arg_init + beqz $r7, .L_clean_reg ! if there isn't _arg_init, go main + addi $sp, $sp, -512 ! allocate space for command line + ! and arguments + move $r6, $sp ! r6 = buffer addr of cmd line + move $r0, $r6 ! r0 = buffer addr of cmd line + syscall SYS_getcmdline ! get cmd line + move $r0, $r6 ! r0 = buffer addr of cmd line + addi $r1, $r6, 256 ! r1 = argv + jral $r7 ! init argc/argv + addi $r1, $r6, 256 ! r1 = argv + b .L_call_main + +.L_clean_reg: /* Prepare argc/argv/env for main function. Since there is no operating system so far, - we set $r0, $r1, and $r2 to be zero. */ + we set $r0, $r1, and $r2 to be zero. + Note: $r2 already set to zero in .L_zero_out_bss: code fragment. */ movi $r0, 0 movi $r1, 0 movi $r2, 0 + +.L_call_main: /* Call 'main'. */ bal main + /* Call _call_exit. */ + ! call _call_exit if necessary; default implementation is in crtexit.c + la $r15, _call_exit ! load address of _call_exit + beqz $r15, .L_terminate_program ! no _call_exit? go exit + jral $r15 ! _call_exit will never return + .L_terminate_program: /* There are two ways to terminate program: 1. User "syscall 0x1" directly. @@ -128,7 +192,7 @@ _start: Currently, we use option 2 as a solution to follow C99 5.1.2.2.3, but aware that general exit() will do some cleanup procedures which may result in large-memory-footprints. */ - + bal exit .L_forever_loop: diff --git a/libgloss/nds32/syscall_extra.h b/libgloss/nds32/syscall_extra.h index 7af4a4550..7c69489ca 100644 --- a/libgloss/nds32/syscall_extra.h +++ b/libgloss/nds32/syscall_extra.h @@ -32,11 +32,12 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. /* These are additional syscalls for nds32 target. */ -#define SYS_rename 3001 -#define SYS_isatty 3002 -#define SYS_system 3003 +#define SYS_rename 3001 +#define SYS_isatty 3002 +#define SYS_system 3003 -#define SYS_geterr 6001 +#define SYS_geterr 6001 +#define SYS_getcmdline 6002 /* Define macros that generate assembly output. */ diff --git a/libgloss/nds32/vh.h b/libgloss/nds32/vh.h index 4ee3e8961..ca3a43f30 100644 --- a/libgloss/nds32/vh.h +++ b/libgloss/nds32/vh.h @@ -43,6 +43,9 @@ BREAK #SWID definition: #define VH_ISATTY 0x7F2B #define VH_SYSTEM 0x7F2C #define VH_GETERR 0x7F2D /* The method we get errno. */ +#define VH_GETPID 0x7F2E +#define VH_KILL 0x7F2F +#define VH_TIMES 0x7F30 /* Define macros that generate assembly output.