about summary refs log tree commit diff
diff options
context:
space:
mode:
authorUlrich Drepper <drepper@redhat.com>2007-08-12 19:03:54 +0000
committerUlrich Drepper <drepper@redhat.com>2007-08-12 19:03:54 +0000
commit75fb247e69ede25fb49929fed7535a091a4f6934 (patch)
treee6c12e73f076abaf5ada25e46159653c12943bcf
parentf47e26262413494427a5c510cb0d2ef3bbbf890f (diff)
downloadglibc-75fb247e69ede25fb49929fed7535a091a4f6934.tar.gz
glibc-75fb247e69ede25fb49929fed7535a091a4f6934.tar.xz
glibc-75fb247e69ede25fb49929fed7535a091a4f6934.zip
* sysdeps/unix/sysv/linux/powerpc/dl-vdso.c: Move to...
	* sysdeps/unix/sysv/linux/dl-vdso.c: ...here.
	* sysdeps/unix/sysv/linux/powerpc/dl-vdso.h: Move to...
	* sysdeps/unix/sysv/linux/dl-vdso.h: ...here.
	* csu/libc-start.c: Pretty printing.
	Use VDSO_SETUP if defined.
	* sysdeps/unix/sysv/linux/powerpc/libc-start.c: Define VDSO_SETUP
	and let generic code call into _libc_vdso_platform_setup.
	* sysdeps/unix/sysv/linux/x86_64/libc-start.c: New file.
	* sysdeps/unix/sysv/linux/x86_64/bits/libc-vdso.h: New file.
	* sysdeps/unix/sysv/linux/x86_64/sysdep.h: Pretty printing.
	Define INLINE_VSYSCALL and INTERNAL_VSYSCALL.
	* sysdeps/unix/sysv/linux/x86_64/Versions: Export __vdso_clock_gettime
	for GLIBC_PRIVATE.
	* sysdeps/unix/sysv/linux/x86_64/Makefile [subdir=elf]
	(sysdep_rountines): Add dl-vdso.

	* sysdeps/unix/sysv/linux/powerpc/Makefile: Use sysdep_routines instead
	of routines.

	* sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h: Add
	attribute_hidden to __vdso_gettimeofday prototype.
-rw-r--r--ChangeLog25
-rw-r--r--csu/libc-start.c12
-rw-r--r--sysdeps/unix/sysv/linux/dl-vdso.c (renamed from sysdeps/unix/sysv/linux/powerpc/dl-vdso.c)0
-rw-r--r--sysdeps/unix/sysv/linux/dl-vdso.h (renamed from sysdeps/unix/sysv/linux/powerpc/dl-vdso.h)0
-rw-r--r--sysdeps/unix/sysv/linux/powerpc/Makefile2
-rw-r--r--sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h2
-rw-r--r--sysdeps/unix/sysv/linux/powerpc/libc-start.c42
-rw-r--r--sysdeps/unix/sysv/linux/x86_64/Makefile4
-rw-r--r--sysdeps/unix/sysv/linux/x86_64/Versions3
-rw-r--r--sysdeps/unix/sysv/linux/x86_64/bits/libc-vdso.h35
-rw-r--r--sysdeps/unix/sysv/linux/x86_64/libc-start.c39
-rw-r--r--sysdeps/unix/sysv/linux/x86_64/sysdep.h206
12 files changed, 266 insertions, 104 deletions
diff --git a/ChangeLog b/ChangeLog
index 3ec150371c..3c6e6b4046 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,28 @@
+2007-08-12  Ulrich Drepper  <drepper@redhat.com>
+
+	* sysdeps/unix/sysv/linux/powerpc/dl-vdso.c: Move to...
+	* sysdeps/unix/sysv/linux/dl-vdso.c: ...here.
+	* sysdeps/unix/sysv/linux/powerpc/dl-vdso.h: Move to...
+	* sysdeps/unix/sysv/linux/dl-vdso.h: ...here.
+	* csu/libc-start.c: Pretty printing.
+	Use VDSO_SETUP if defined.
+	* sysdeps/unix/sysv/linux/powerpc/libc-start.c: Define VDSO_SETUP
+	and let generic code call into _libc_vdso_platform_setup.
+	* sysdeps/unix/sysv/linux/x86_64/libc-start.c: New file.
+	* sysdeps/unix/sysv/linux/x86_64/bits/libc-vdso.h: New file.
+	* sysdeps/unix/sysv/linux/x86_64/sysdep.h: Pretty printing.
+	Define INLINE_VSYSCALL and INTERNAL_VSYSCALL.
+	* sysdeps/unix/sysv/linux/x86_64/Versions: Export __vdso_clock_gettime
+	for GLIBC_PRIVATE.
+	* sysdeps/unix/sysv/linux/x86_64/Makefile [subdir=elf]
+	(sysdep_rountines): Add dl-vdso.
+
+	* sysdeps/unix/sysv/linux/powerpc/Makefile: Use sysdep_routines instead
+	of routines.
+
+	* sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h: Add
+	attribute_hidden to __vdso_gettimeofday prototype.
+
 2007-08-12  Roland McGrath  <roland@redhat.com>
 
 	* manual/stdio.texi (Variable Arguments Output): Fix xref to gcc manual.
diff --git a/csu/libc-start.c b/csu/libc-start.c
index 0ed993651e..d3eadeb704 100644
--- a/csu/libc-start.c
+++ b/csu/libc-start.c
@@ -138,16 +138,18 @@ LIBC_START_MAIN (int (*main) (int, char **, char ** MAIN_AUXVEC_DECL),
      functions are using thread functions if these are available and
      we need to setup errno.  */
   __pthread_initialize_minimal ();
-#endif
 
-# ifndef SHARED
   /* Set up the stack checker's canary.  */
   uintptr_t stack_chk_guard = _dl_setup_stack_chk_guard ();
-#  ifdef THREAD_SET_STACK_GUARD
+# ifdef THREAD_SET_STACK_GUARD
   THREAD_SET_STACK_GUARD (stack_chk_guard);
-#  else
+# else
   __stack_chk_guard = stack_chk_guard;
-#  endif
+# endif
+#endif
+
+#ifdef VDSO_SETUP
+  VDSO_SETUP ();
 #endif
 
   /* Register the destructor of the dynamic linker if there is any.  */
diff --git a/sysdeps/unix/sysv/linux/powerpc/dl-vdso.c b/sysdeps/unix/sysv/linux/dl-vdso.c
index e1be097734..e1be097734 100644
--- a/sysdeps/unix/sysv/linux/powerpc/dl-vdso.c
+++ b/sysdeps/unix/sysv/linux/dl-vdso.c
diff --git a/sysdeps/unix/sysv/linux/powerpc/dl-vdso.h b/sysdeps/unix/sysv/linux/dl-vdso.h
index a7dcb2e5ff..a7dcb2e5ff 100644
--- a/sysdeps/unix/sysv/linux/powerpc/dl-vdso.h
+++ b/sysdeps/unix/sysv/linux/dl-vdso.h
diff --git a/sysdeps/unix/sysv/linux/powerpc/Makefile b/sysdeps/unix/sysv/linux/powerpc/Makefile
index ecd8057951..d1281cf469 100644
--- a/sysdeps/unix/sysv/linux/powerpc/Makefile
+++ b/sysdeps/unix/sysv/linux/powerpc/Makefile
@@ -8,5 +8,5 @@ gen-as-const-headers += ucontext_i.sym
 endif
 
 ifeq ($(subdir),elf)
-routines += dl-vdso
+sysdep_routines += dl-vdso
 endif
diff --git a/sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h b/sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h
index f20a5a175c..746d9ced4a 100644
--- a/sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h
+++ b/sysdeps/unix/sysv/linux/powerpc/bits/libc-vdso.h
@@ -23,7 +23,7 @@
 
 #ifdef SHARED
 
-extern void *__vdso_gettimeofday;
+extern void *__vdso_gettimeofday attribute_hidden;
 
 extern void *__vdso_clock_gettime;
 
diff --git a/sysdeps/unix/sysv/linux/powerpc/libc-start.c b/sysdeps/unix/sysv/linux/powerpc/libc-start.c
index a71cfa5b06..d78876d40d 100644
--- a/sysdeps/unix/sysv/linux/powerpc/libc-start.c
+++ b/sysdeps/unix/sysv/linux/powerpc/libc-start.c
@@ -24,23 +24,6 @@
 #include <bp-start.h>
 #include <bp-sym.h>
 
-int __cache_line_size attribute_hidden;
-/* The main work is done in the generic function.  */
-#define LIBC_START_MAIN generic_start_main
-#define LIBC_START_DISABLE_INLINE
-#define LIBC_START_MAIN_AUXVEC_ARG
-#define MAIN_AUXVEC_ARG
-#define INIT_MAIN_ARGS
-#include <csu/libc-start.c>
-
-struct startup_info
-  {
-    void *__unbounded sda_base;
-    int (*main) (int, char **, char **, void *);
-    int (*init) (int, char **, char **, void *);
-    void (*fini) (void);
-  };
-
 
 #ifdef SHARED
 # include <sys/time.h>
@@ -69,8 +52,28 @@ static inline void _libc_vdso_platform_setup (void)
     __vdso_get_tbfreq = _dl_vdso_vsym ("__kernel_vdso_get_tbfreq",
 				       "LINUX_2.6.15");
   }
+
+# define VDSO_SETUP _libc_vdso_platform_setup
 #endif
 
+
+int __cache_line_size attribute_hidden;
+/* The main work is done in the generic function.  */
+#define LIBC_START_MAIN generic_start_main
+#define LIBC_START_DISABLE_INLINE
+#define LIBC_START_MAIN_AUXVEC_ARG
+#define MAIN_AUXVEC_ARG
+#define INIT_MAIN_ARGS
+#include <csu/libc-start.c>
+
+struct startup_info
+  {
+    void *__unbounded sda_base;
+    int (*main) (int, char **, char **, void *);
+    int (*init) (int, char **, char **, void *);
+    void (*fini) (void);
+  };
+
 int
 /* GKM FIXME: GCC: this should get __BP_ prefix by virtue of the
    BPs in the arglist of startup_info.main and startup_info.init. */
@@ -117,10 +120,7 @@ int
 	__cache_line_size = av->a_un.a_val;
 	break;
       }
-#ifdef SHARED
-  /* Resolve and initialize function pointers for VDSO functions.  */
-  _libc_vdso_platform_setup ();
-#endif
+
   return generic_start_main (stinfo->main, argc, ubp_av, auxvec,
 			     stinfo->init, stinfo->fini, rtld_fini,
 			     stack_on_entry);
diff --git a/sysdeps/unix/sysv/linux/x86_64/Makefile b/sysdeps/unix/sysv/linux/x86_64/Makefile
index bdad5063df..6e2741a967 100644
--- a/sysdeps/unix/sysv/linux/x86_64/Makefile
+++ b/sysdeps/unix/sysv/linux/x86_64/Makefile
@@ -13,3 +13,7 @@ endif
 ifeq ($(subdir),csu)
 gen-as-const-headers += ucontext_i.sym
 endif
+
+ifeq ($(subdir),elf)
+sysdep_routines += dl-vdso
+endif
diff --git a/sysdeps/unix/sysv/linux/x86_64/Versions b/sysdeps/unix/sysv/linux/x86_64/Versions
index fd1b3cc296..34c100bfd2 100644
--- a/sysdeps/unix/sysv/linux/x86_64/Versions
+++ b/sysdeps/unix/sysv/linux/x86_64/Versions
@@ -6,4 +6,7 @@ libc {
 
     modify_ldt;
   }
+  GLIBC_PRIVATE {
+    __vdso_clock_gettime;
+  }
 }
diff --git a/sysdeps/unix/sysv/linux/x86_64/bits/libc-vdso.h b/sysdeps/unix/sysv/linux/x86_64/bits/libc-vdso.h
new file mode 100644
index 0000000000..6e08d3b203
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/bits/libc-vdso.h
@@ -0,0 +1,35 @@
+/* Resolve function pointers to VDSO functions.
+   Copyright (C) 2005, 2007 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#ifndef _LIBC_VDSO_H
+#define _LIBC_VDSO_H
+
+#include <time.h>
+#include <sys/time.h>
+
+#ifdef SHARED
+
+extern int (*__vdso_gettimeofday) (struct timeval *, void *)
+  attribute_hidden;
+
+extern int (*__vdso_clock_gettime) (clockid_t, struct timespec *);
+
+#endif
+
+#endif /* _LIBC_VDSO_H */
diff --git a/sysdeps/unix/sysv/linux/x86_64/libc-start.c b/sysdeps/unix/sysv/linux/x86_64/libc-start.c
new file mode 100644
index 0000000000..3c95729371
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/libc-start.c
@@ -0,0 +1,39 @@
+/* Copyright (C) 2007 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, write to the Free
+   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+   02111-1307 USA.  */
+
+#ifdef SHARED
+# include <dl-vdso.h>
+# include <bits/libc-vdso.h>
+
+int (*__vdso_gettimeofday) (struct timeval *, void *) attribute_hidden;
+
+int (*__vdso_clock_gettime) (clockid_t, struct timespec *);
+
+
+static inline void
+_libc_vdso_platform_setup (void)
+{
+  __vdso_gettimeofday = _dl_vdso_vsym ("gettimeofday", "LINUX_2.6");
+
+  __vdso_clock_gettime = _dl_vdso_vsym ("clock_gettime", "LINUX_2.6");
+}
+
+# define VDSO_SETUP _libc_vdso_platform_setup
+#endif
+
+#include <csu/libc-start.c>
diff --git a/sysdeps/unix/sysv/linux/x86_64/sysdep.h b/sysdeps/unix/sysv/linux/x86_64/sysdep.h
index 1d9a68a046..61701a2869 100644
--- a/sysdeps/unix/sysv/linux/x86_64/sysdep.h
+++ b/sysdeps/unix/sysv/linux/x86_64/sysdep.h
@@ -68,14 +68,14 @@
 
 /* We don't want the label for the error handle to be global when we define
    it here.  */
-#ifdef PIC
-# define SYSCALL_ERROR_LABEL 0f
-#else
-# define SYSCALL_ERROR_LABEL syscall_error
-#endif
+# ifdef PIC
+#  define SYSCALL_ERROR_LABEL 0f
+# else
+#  define SYSCALL_ERROR_LABEL syscall_error
+# endif
 
-#undef	PSEUDO
-#define	PSEUDO(name, syscall_name, args)				      \
+# undef	PSEUDO
+# define PSEUDO(name, syscall_name, args)				      \
   .text;								      \
   ENTRY (name)								      \
     DO_CALL (syscall_name, args);					      \
@@ -83,40 +83,40 @@
     jae SYSCALL_ERROR_LABEL;						      \
   L(pseudo_end):
 
-#undef	PSEUDO_END
-#define	PSEUDO_END(name)						      \
+# undef	PSEUDO_END
+# define PSEUDO_END(name)						      \
   SYSCALL_ERROR_HANDLER							      \
   END (name)
 
-#undef	PSEUDO_NOERRNO
-#define	PSEUDO_NOERRNO(name, syscall_name, args) \
+# undef	PSEUDO_NOERRNO
+# define PSEUDO_NOERRNO(name, syscall_name, args) \
   .text;								      \
   ENTRY (name)								      \
     DO_CALL (syscall_name, args)
 
-#undef	PSEUDO_END_NOERRNO
-#define	PSEUDO_END_NOERRNO(name) \
+# undef	PSEUDO_END_NOERRNO
+# define PSEUDO_END_NOERRNO(name) \
   END (name)
 
-#define ret_NOERRNO ret
+# define ret_NOERRNO ret
 
-#undef	PSEUDO_ERRVAL
-#define	PSEUDO_ERRVAL(name, syscall_name, args) \
+# undef	PSEUDO_ERRVAL
+# define PSEUDO_ERRVAL(name, syscall_name, args) \
   .text;								      \
   ENTRY (name)								      \
     DO_CALL (syscall_name, args);					      \
     negq %rax
 
-#undef	PSEUDO_END_ERRVAL
-#define	PSEUDO_END_ERRVAL(name) \
+# undef	PSEUDO_END_ERRVAL
+# define PSEUDO_END_ERRVAL(name) \
   END (name)
 
-#define ret_ERRVAL ret
+# define ret_ERRVAL ret
 
-#ifndef PIC
-#define SYSCALL_ERROR_HANDLER	/* Nothing here; code in sysdep.S is used.  */
-#elif RTLD_PRIVATE_ERRNO
-# define SYSCALL_ERROR_HANDLER			\
+# ifndef PIC
+#  define SYSCALL_ERROR_HANDLER	/* Nothing here; code in sysdep.S is used.  */
+# elif RTLD_PRIVATE_ERRNO
+#  define SYSCALL_ERROR_HANDLER			\
 0:						\
   leaq rtld_errno(%rip), %rcx;			\
   xorl %edx, %edx;				\
@@ -124,13 +124,13 @@
   movl %edx, (%rcx);				\
   orq $-1, %rax;				\
   jmp L(pseudo_end);
-#elif USE___THREAD
-# ifndef NOT_IN_libc
-#  define SYSCALL_ERROR_ERRNO __libc_errno
-# else
-#  define SYSCALL_ERROR_ERRNO errno
-# endif
-# define SYSCALL_ERROR_HANDLER			\
+# elif USE___THREAD
+#  ifndef NOT_IN_libc
+#   define SYSCALL_ERROR_ERRNO __libc_errno
+#  else
+#   define SYSCALL_ERROR_ERRNO errno
+#  endif
+#  define SYSCALL_ERROR_HANDLER			\
 0:						\
   movq SYSCALL_ERROR_ERRNO@GOTTPOFF(%rip), %rcx;\
   xorl %edx, %edx;				\
@@ -138,10 +138,10 @@
   movl %edx, %fs:(%rcx);			\
   orq $-1, %rax;				\
   jmp L(pseudo_end);
-#elif defined _LIBC_REENTRANT
+# elif defined _LIBC_REENTRANT
 /* Store (- %rax) into errno through the GOT.
    Note that errno occupies only 4 bytes.  */
-# define SYSCALL_ERROR_HANDLER			\
+#  define SYSCALL_ERROR_HANDLER			\
 0:						\
   xorl %edx, %edx;				\
   subq %rax, %rdx;				\
@@ -158,15 +158,15 @@
 
 /* A quick note: it is assumed that the call to `__errno_location' does
    not modify the stack!  */
-#else /* Not _LIBC_REENTRANT.  */
-# define SYSCALL_ERROR_HANDLER			\
+# else /* Not _LIBC_REENTRANT.  */
+#  define SYSCALL_ERROR_HANDLER			\
 0:movq errno@GOTPCREL(%RIP), %rcx;		\
   xorl %edx, %edx;				\
   subq %rax, %rdx;				\
   movl %edx, (%rcx);				\
   orq $-1, %rax;				\
   jmp L(pseudo_end);
-#endif	/* PIC */
+# endif	/* PIC */
 
 /* The Linux/x86-64 kernel expects the system call parameters in
    registers according to the following table:
@@ -204,25 +204,25 @@
 
     Syscalls of more than 6 arguments are not supported.  */
 
-#undef	DO_CALL
-#define DO_CALL(syscall_name, args)		\
+# undef	DO_CALL
+# define DO_CALL(syscall_name, args)		\
     DOARGS_##args				\
     movl $SYS_ify (syscall_name), %eax;		\
     syscall;
 
-#define DOARGS_0 /* nothing */
-#define DOARGS_1 /* nothing */
-#define DOARGS_2 /* nothing */
-#define DOARGS_3 /* nothing */
-#define DOARGS_4 movq %rcx, %r10;
-#define DOARGS_5 DOARGS_4
-#define DOARGS_6 DOARGS_5
+# define DOARGS_0 /* nothing */
+# define DOARGS_1 /* nothing */
+# define DOARGS_2 /* nothing */
+# define DOARGS_3 /* nothing */
+# define DOARGS_4 movq %rcx, %r10;
+# define DOARGS_5 DOARGS_4
+# define DOARGS_6 DOARGS_5
 
 #else	/* !__ASSEMBLER__ */
 /* Define a macro which expands inline into the wrapper code for a system
    call.  */
-#undef INLINE_SYSCALL
-#define INLINE_SYSCALL(name, nr, args...) \
+# undef INLINE_SYSCALL
+# define INLINE_SYSCALL(name, nr, args...) \
   ({									      \
     unsigned long resultvar = INTERNAL_SYSCALL (name, , nr, args);	      \
     if (__builtin_expect (INTERNAL_SYSCALL_ERROR_P (resultvar, ), 0))	      \
@@ -232,10 +232,10 @@
       }									      \
     (long) resultvar; })
 
-#undef INTERNAL_SYSCALL_DECL
-#define INTERNAL_SYSCALL_DECL(err) do { } while (0)
+# undef INTERNAL_SYSCALL_DECL
+# define INTERNAL_SYSCALL_DECL(err) do { } while (0)
 
-#define INTERNAL_SYSCALL_NCS(name, err, nr, args...) \
+# define INTERNAL_SYSCALL_NCS(name, err, nr, args...) \
   ({									      \
     unsigned long resultvar;						      \
     LOAD_ARGS_##nr (args)						      \
@@ -245,68 +245,122 @@
     : "=a" (resultvar)							      \
     : "0" (name) ASM_ARGS_##nr : "memory", "cc", "r11", "cx");		      \
     (long) resultvar; })
-#undef INTERNAL_SYSCALL
-#define INTERNAL_SYSCALL(name, err, nr, args...) \
+# undef INTERNAL_SYSCALL
+# define INTERNAL_SYSCALL(name, err, nr, args...) \
   INTERNAL_SYSCALL_NCS (__NR_##name, err, nr, ##args)
 
-#undef INTERNAL_SYSCALL_ERROR_P
-#define INTERNAL_SYSCALL_ERROR_P(val, err) \
+# undef INTERNAL_SYSCALL_ERROR_P
+# define INTERNAL_SYSCALL_ERROR_P(val, err) \
   ((unsigned long) (val) >= -4095L)
 
-#undef INTERNAL_SYSCALL_ERRNO
-#define INTERNAL_SYSCALL_ERRNO(val, err)	(-(val))
+# undef INTERNAL_SYSCALL_ERRNO
+# define INTERNAL_SYSCALL_ERRNO(val, err)	(-(val))
+
+# ifdef SHARED
+#  define INLINE_VSYSCALL(name, nr, args...) \
+  ({									      \
+    __label__ out;							      \
+    __label__ iserr;							      \
+    INTERNAL_SYSCALL_DECL (sc_err);					      \
+    long int sc_ret;							      \
+									      \
+    if (__vdso_##name != NULL)						      \
+      {									      \
+	sc_ret = __vdso_##name (args);					      \
+	if (!INTERNAL_SYSCALL_ERROR_P (sc_ret, sc_err))			      \
+	  goto out;							      \
+	if (INTERNAL_SYSCALL_ERRNO (sc_ret, sc_err) != ENOSYS)		      \
+	  goto iserr;							      \
+      }									      \
+									      \
+    sc_ret = INTERNAL_SYSCALL (name, sc_err, nr, ##args);		      \
+    if (INTERNAL_SYSCALL_ERROR_P (sc_ret, sc_err))			      \
+      {									      \
+      iserr:								      \
+        __set_errno (INTERNAL_SYSCALL_ERRNO (sc_ret, sc_err));		      \
+        sc_ret = -1L;							      \
+      }									      \
+  out:									      \
+    sc_ret;								      \
+  })
+#  define INTERNAL_VSYSCALL(name, err, nr, args...) \
+  ({									      \
+    __label__ out;							      \
+    long int v_ret;							      \
+									      \
+    if (__vdso_##name != NULL)						      \
+      {									      \
+	v_ret = __vdso_##name (args);					      \
+	if (!INTERNAL_SYSCALL_ERROR_P (v_ret, err)			      \
+	    || INTERNAL_SYSCALL_ERRNO (v_ret, err) != ENOSYS)		      \
+	  goto out;							      \
+      }									      \
+    v_ret = INTERNAL_SYSCALL (name, err, nr, ##args);			      \
+  out:									      \
+    v_ret;								      \
+  })
+
+/* List of system calls which are supported as vsyscalls.  */
+#  define HAVE_CLOCK_GETTIME_VSYSCALL	1
+
+# else
+#  define INLINE_VSYSCALL(name, nr, args...) \
+  INLINE_SYSCALL (name, nr, ##args)
+#  define INTERNAL_VSYSCALL(name, err, nr, args...) \
+  INTERNAL_SYSCALL (name, err, nr, ##args)
+# endif
 
-#define LOAD_ARGS_0()
-#define LOAD_REGS_0
-#define ASM_ARGS_0
+# define LOAD_ARGS_0()
+# define LOAD_REGS_0
+# define ASM_ARGS_0
 
-#define LOAD_ARGS_1(a1)					\
+# define LOAD_ARGS_1(a1)				\
   long int __arg1 = (long) (a1);			\
   LOAD_ARGS_0 ()
-#define LOAD_REGS_1					\
+# define LOAD_REGS_1					\
   register long int _a1 asm ("rdi") = __arg1;		\
   LOAD_REGS_0
-#define ASM_ARGS_1	ASM_ARGS_0, "r" (_a1)
+# define ASM_ARGS_1	ASM_ARGS_0, "r" (_a1)
 
-#define LOAD_ARGS_2(a1, a2)				\
+# define LOAD_ARGS_2(a1, a2)				\
   long int __arg2 = (long) (a2);			\
   LOAD_ARGS_1 (a1)
-#define LOAD_REGS_2					\
+# define LOAD_REGS_2					\
   register long int _a2 asm ("rsi") = __arg2;		\
   LOAD_REGS_1
-#define ASM_ARGS_2	ASM_ARGS_1, "r" (_a2)
+# define ASM_ARGS_2	ASM_ARGS_1, "r" (_a2)
 
-#define LOAD_ARGS_3(a1, a2, a3)				\
+# define LOAD_ARGS_3(a1, a2, a3)			\
   long int __arg3 = (long) (a3);			\
   LOAD_ARGS_2 (a1, a2)
-#define LOAD_REGS_3					\
+# define LOAD_REGS_3					\
   register long int _a3 asm ("rdx") = __arg3;		\
   LOAD_REGS_2
-#define ASM_ARGS_3	ASM_ARGS_2, "r" (_a3)
+# define ASM_ARGS_3	ASM_ARGS_2, "r" (_a3)
 
-#define LOAD_ARGS_4(a1, a2, a3, a4)			\
+# define LOAD_ARGS_4(a1, a2, a3, a4)			\
   long int __arg4 = (long) (a4);			\
   LOAD_ARGS_3 (a1, a2, a3)
-#define LOAD_REGS_4					\
+# define LOAD_REGS_4					\
   register long int _a4 asm ("r10") = __arg4;		\
   LOAD_REGS_3
-#define ASM_ARGS_4	ASM_ARGS_3, "r" (_a4)
+# define ASM_ARGS_4	ASM_ARGS_3, "r" (_a4)
 
-#define LOAD_ARGS_5(a1, a2, a3, a4, a5)			\
+# define LOAD_ARGS_5(a1, a2, a3, a4, a5)		\
   long int __arg5 = (long) (a5);			\
   LOAD_ARGS_4 (a1, a2, a3, a4)
-#define LOAD_REGS_5					\
+# define LOAD_REGS_5					\
   register long int _a5 asm ("r8") = __arg5;		\
   LOAD_REGS_4
-#define ASM_ARGS_5	ASM_ARGS_4, "r" (_a5)
+# define ASM_ARGS_5	ASM_ARGS_4, "r" (_a5)
 
-#define LOAD_ARGS_6(a1, a2, a3, a4, a5, a6)		\
+# define LOAD_ARGS_6(a1, a2, a3, a4, a5, a6)		\
   long int __arg6 = (long) (a6);			\
   LOAD_ARGS_5 (a1, a2, a3, a4, a5)
-#define LOAD_REGS_6					\
+# define LOAD_REGS_6					\
   register long int _a6 asm ("r9") = __arg6;		\
   LOAD_REGS_5
-#define ASM_ARGS_6	ASM_ARGS_5, "r" (_a6)
+# define ASM_ARGS_6	ASM_ARGS_5, "r" (_a6)
 
 #endif	/* __ASSEMBLER__ */