nvptx: Emulate clock and other machine stubs.

This patch to the libc/machine/nvptx port of newlib implements an
approximation of "clock" and provides some additional stub routines.
These changes not only reduce the number of (link) failures in the GCC
testsuite when targeting nvptx-none, but also allow the NIST scimark4
benchmark to compile and run without modification.

newlib already contains support for backends to provide their own
clock implementations via -DCLOCK_PROVIDED.  That functionality is
used here to return an approximate elapsed time based on the NVidia
GPU's clock64 cycle counter.  Although not great, this is better than
the current behaviour of link error from the unresolved symbol
_times_r.

The other part of the patch is to add a small number of stub functions
to nvptx's misc.c.  Adding isatty, for example, resolves linking
problems in libc from the dependency in __smakebuf_r, and the sync
stub, for example, fixes the failure with GCC's
testsuite/gfortran.dg/ISO_Fortran_binding_14.f90 [which simply tests
that gfortran can call a/any C function].

newlib/
        configure.host: Add -DCLOCK_PROVIDED to newlib_cflags on nvptx*.

newlib/libc/machine/nvptx
        Makefile.am: Add clock.c to lib_a_SOURCES.
        clock.c: New source file to implement/approximate clock().
        misc.c: Add stubs for fstat, isatty, open, sync and unlink.
This commit is contained in:
Roger Sayle 2021-08-24 17:24:19 +01:00 committed by Corinna Vinschen
parent 1a821390d1
commit 6bb96d13a2
6 changed files with 56 additions and 4 deletions

View File

@ -289,7 +289,7 @@ case "${host_cpu}" in
;; ;;
nvptx*) nvptx*)
machine_dir=nvptx machine_dir=nvptx
newlib_cflags="${newlib_cflags} -DMALLOC_PROVIDED" newlib_cflags="${newlib_cflags} -DCLOCK_PROVIDED -DMALLOC_PROVIDED"
;; ;;
or1k*|or1knd*) or1k*|or1knd*)
machine_dir=or1k machine_dir=or1k

View File

@ -10,7 +10,7 @@ noinst_LIBRARIES = lib.a
lib_a_SOURCES = calloc.c callocr.c malloc.c mallocr.c realloc.c reallocr.c \ lib_a_SOURCES = calloc.c callocr.c malloc.c mallocr.c realloc.c reallocr.c \
free.c write.c assert.c puts.c putchar.c printf.c abort.c \ free.c write.c assert.c puts.c putchar.c printf.c abort.c \
exit.c misc.c exit.c misc.c clock.c
lib_a_CFLAGS = $(AM_CFLAGS) lib_a_CFLAGS = $(AM_CFLAGS)
ACLOCAL_AMFLAGS = -I ../../.. -I ../../../.. ACLOCAL_AMFLAGS = -I ../../.. -I ../../../..

View File

@ -76,7 +76,7 @@ am_lib_a_OBJECTS = lib_a-calloc.$(OBJEXT) lib_a-callocr.$(OBJEXT) \
lib_a-assert.$(OBJEXT) lib_a-puts.$(OBJEXT) \ lib_a-assert.$(OBJEXT) lib_a-puts.$(OBJEXT) \
lib_a-putchar.$(OBJEXT) lib_a-printf.$(OBJEXT) \ lib_a-putchar.$(OBJEXT) lib_a-printf.$(OBJEXT) \
lib_a-abort.$(OBJEXT) lib_a-exit.$(OBJEXT) \ lib_a-abort.$(OBJEXT) lib_a-exit.$(OBJEXT) \
lib_a-misc.$(OBJEXT) lib_a-misc.$(OBJEXT) lib_a-clock.$(OBJEXT)
lib_a_OBJECTS = $(am_lib_a_OBJECTS) lib_a_OBJECTS = $(am_lib_a_OBJECTS)
DEFAULT_INCLUDES = -I.@am__isrc@ DEFAULT_INCLUDES = -I.@am__isrc@
depcomp = depcomp =
@ -188,6 +188,7 @@ prefix = @prefix@
program_transform_name = @program_transform_name@ program_transform_name = @program_transform_name@
psdir = @psdir@ psdir = @psdir@
sbindir = @sbindir@ sbindir = @sbindir@
shared_machine_dir = @shared_machine_dir@
sharedstatedir = @sharedstatedir@ sharedstatedir = @sharedstatedir@
srcdir = @srcdir@ srcdir = @srcdir@
sys_dir = @sys_dir@ sys_dir = @sys_dir@
@ -202,7 +203,7 @@ AM_CCASFLAGS = $(INCLUDES)
noinst_LIBRARIES = lib.a noinst_LIBRARIES = lib.a
lib_a_SOURCES = calloc.c callocr.c malloc.c mallocr.c realloc.c reallocr.c \ lib_a_SOURCES = calloc.c callocr.c malloc.c mallocr.c realloc.c reallocr.c \
free.c write.c assert.c puts.c putchar.c printf.c abort.c \ free.c write.c assert.c puts.c putchar.c printf.c abort.c \
exit.c misc.c exit.c misc.c clock.c
lib_a_CFLAGS = $(AM_CFLAGS) lib_a_CFLAGS = $(AM_CFLAGS)
ACLOCAL_AMFLAGS = -I ../../.. -I ../../../.. ACLOCAL_AMFLAGS = -I ../../.. -I ../../../..
@ -355,6 +356,12 @@ lib_a-misc.o: misc.c
lib_a-misc.obj: misc.c lib_a-misc.obj: misc.c
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_a_CFLAGS) $(CFLAGS) -c -o lib_a-misc.obj `if test -f 'misc.c'; then $(CYGPATH_W) 'misc.c'; else $(CYGPATH_W) '$(srcdir)/misc.c'; fi` $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_a_CFLAGS) $(CFLAGS) -c -o lib_a-misc.obj `if test -f 'misc.c'; then $(CYGPATH_W) 'misc.c'; else $(CYGPATH_W) '$(srcdir)/misc.c'; fi`
lib_a-clock.o: clock.c
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_a_CFLAGS) $(CFLAGS) -c -o lib_a-clock.o `test -f 'clock.c' || echo '$(srcdir)/'`clock.c
lib_a-clock.obj: clock.c
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_a_CFLAGS) $(CFLAGS) -c -o lib_a-clock.obj `if test -f 'clock.c'; then $(CYGPATH_W) 'clock.c'; else $(CYGPATH_W) '$(srcdir)/clock.c'; fi`
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES) ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \ list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \ unique=`for i in $$list; do \

View File

@ -0,0 +1,18 @@
/* clock.c
* Support file for nvptx in newlib.
*/
#include <time.h>
clock_t
clock ()
{
unsigned long long now;
#if __PTX_SM__ >= 310
asm volatile("mov.u64 %0, %%globaltimer;" : "=r"(now));
return now/((1000000000ull)/CLOCKS_PER_SEC);
#else
asm volatile("mov.u64 %0, %%clock64;" : "=r"(now));
// Assume a GPU base clock frequency of 1250MHz.
return now/((1250000000ull)/CLOCKS_PER_SEC);
#endif
}

View File

@ -565,6 +565,7 @@ ac_unique_file="Makefile.am"
ac_subst_vars='LTLIBOBJS ac_subst_vars='LTLIBOBJS
LIBOBJS LIBOBJS
sys_dir sys_dir
shared_machine_dir
machine_dir machine_dir
libm_machine_dir libm_machine_dir
lpfx lpfx
@ -3428,6 +3429,7 @@ OBJEXT=${oext}
ac_config_files="$ac_config_files Makefile" ac_config_files="$ac_config_files Makefile"
cat >confcache <<\_ACEOF cat >confcache <<\_ACEOF

View File

@ -15,6 +15,7 @@
#include <errno.h> #include <errno.h>
#include <sys/types.h> #include <sys/types.h>
#include <sys/stat.h>
#undef errno #undef errno
extern int errno; extern int errno;
@ -23,12 +24,36 @@ close(int fd) {
return -1; return -1;
} }
int
fstat (int fd, struct stat *buf) {
return -1;
}
int
isatty (int fd) {
return fd == 1;
}
off_t off_t
lseek(int fd, off_t offset, int whence) { lseek(int fd, off_t offset, int whence) {
return 0; return 0;
} }
int
open (const char *pathname, int flags, ...) {
return -1;
}
int int
read(int fd, void *buf, size_t count) { read(int fd, void *buf, size_t count) {
return 0; return 0;
} }
void
sync (void) {
}
int
unlink (const char *pathname) {
return -1;
}