This is the mail archive of the glibc-cvs@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

GNU C Library master sources branch rth/execl created. glibc-2.22-720-g5b78856


This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "GNU C Library master sources".

The branch, rth/execl has been created
        at  5b78856069a21550d4b67b4c0a269915f37fce0f (commit)

- Log -----------------------------------------------------------------
http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=5b78856069a21550d4b67b4c0a269915f37fce0f

commit 5b78856069a21550d4b67b4c0a269915f37fce0f
Author: Richard Henderson <rth@twiddle.net>
Date:   Tue Feb 9 13:43:08 2016 +1100

    alpha: Implement execl{,e,p} without double stack allocation

diff --git a/sysdeps/unix/sysv/linux/alpha/execl.S b/sysdeps/unix/sysv/linux/alpha/execl.S
new file mode 100644
index 0000000..11f4307
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/alpha/execl.S
@@ -0,0 +1,52 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execl)
+	cfi_startproc
+	ldgp	gp, 0(pv)
+	lda	sp, -48(sp)
+	cfi_adjust_cfa_offset(48)
+	.frame	sp, 48, ra
+	.prologue 1
+
+	/* Save the portions of the argv argument list in registers.  */
+	stq	a5, 40(sp)
+	stq	a4, 32(sp)
+	stq	a3, 24(sp)
+	stq	a2, 16(sp)
+	stq	a1,  8(sp)
+
+	/* Load the argv and envp arguments; path is already in place.  */
+	lda	a1, 8(sp)
+	ldq	a2, __environ
+
+	lda	v0, SYS_ify(execve)
+	call_pal PAL_callsys
+
+	/* Discard the stack frame now.  */
+	lda	sp, 48(sp)
+	cfi_adjust_cfa_offset(-48)
+
+	/* All returns are errors.  */
+	br	SYSCALL_ERROR_LABEL
+
+PSEUDO_END (execle)
+	cfi_endproc
+
+libc_hidden_def (execl)
diff --git a/sysdeps/unix/sysv/linux/alpha/execle.S b/sysdeps/unix/sysv/linux/alpha/execle.S
new file mode 100644
index 0000000..ce75ce3
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/alpha/execle.S
@@ -0,0 +1,58 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execle)
+	cfi_startproc
+	lda	sp, -48(sp)
+	cfi_adjust_cfa_offset(48)
+	.frame  sp, 48, ra
+	.prologue 0
+
+	/* Save the portions of the argv argument list in registers.  */
+	stq	a5, 40(sp)
+	stq	a4, 32(sp)
+	stq	a3, 24(sp)
+	stq	a2, 16(sp)
+	stq	a1,  8(sp)
+
+	/* Find the env argument.  It is the array element after the argv
+	   NULL terminator, which cannot be located before argv[1].  */
+	lda	t0, 16(sp)
+1:	ldq	t1, 0(t0)
+	addq	t0, 8, t0
+	bne	t1, 1b
+
+	/* Load the argv and envp arguments; path is already in place.  */
+	lda	a1, 8(sp)
+	ldq	a2, 0(t0)
+
+	lda	v0, SYS_ify(execve)
+	call_pal PAL_callsys
+
+	/* Discard the stack frame now.  */
+	lda	sp, 48(sp)
+	cfi_adjust_cfa_offset(-48)
+
+	/* All returns are errors.  */
+	br	SYSCALL_ERROR_LABEL
+
+PSEUDO_END (execle)
+	cfi_endproc
+
+libc_hidden_def (execle)
diff --git a/sysdeps/unix/sysv/linux/alpha/execlp.S b/sysdeps/unix/sysv/linux/alpha/execlp.S
new file mode 100644
index 0000000..b0ef76d
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/alpha/execlp.S
@@ -0,0 +1,53 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execlp)
+	cfi_startproc
+	ldgp	gp, 0(pv)
+	lda	sp, -48(sp)
+	cfi_adjust_cfa_offset(48)
+	stq	ra, 0(sp)
+	cfi_rel_offset(ra, 0)
+	.prologue 1
+
+	/* Save the portions of the argv argument list in registers.  */
+	stq	a5, 40(sp)
+	stq	a4, 32(sp)
+	stq	a3, 24(sp)
+	stq	a2, 16(sp)
+	stq	a1,  8(sp)
+
+	/* Load the argv and envp arguments; path is already in place.  */
+	lda	a1, 8(sp)
+	ldq	a2, __environ
+#ifdef PIC
+	bsr	ra, __execvpe		!samegp
+#else
+	jsr	ra, __execvpe
+	ldgp	gp, 0(ra)
+#endif
+
+	lda	sp, 48(sp)
+	cfi_adjust_cfa_offset(-48)
+	ret
+
+END (execlp)
+	cfi_endproc
+
+libc_hidden_def (execlp)

http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=4577d8457637adac28ed34bc3f9ce0a936dc786e

commit 4577d8457637adac28ed34bc3f9ce0a936dc786e
Author: Richard Henderson <rth@twiddle.net>
Date:   Tue Feb 9 15:19:32 2016 +1100

    x32: Implement execl{,e,p} without double stack allocation

diff --git a/sysdeps/unix/sysv/linux/x86_64/x32/execl.S b/sysdeps/unix/sysv/linux/x86_64/x32/execl.S
new file mode 100644
index 0000000..9139bad
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/x32/execl.S
@@ -0,0 +1,88 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execl)
+	/* Move return address into a register.  */
+	pop	%rax
+	cfi_adjust_cfa_offset(-8)
+	cfi_register(%rip, %rax)
+
+	/* Save the arguments in registers.  Stop as soon as we detect
+	   the NULL terminator, as if we find one, we do not want to fall
+	   into the on-stack conversion loop.  */
+	sub	$24, %esp
+	cfi_adjust_cfa_offset(24)
+
+	mov	%edi, 4(%rsp)	/* argv[0] must be non-null.  */
+
+	mov	%edx, 8(%rsp)
+	test	%edx, %edx
+	jz	9f
+
+	mov	%ecx, 12(%rsp)
+	test	%ecx, %ecx
+	jz	9f
+
+	mov	%r8d, 16(%rsp)
+	test	%r8d, %r8d
+	jz	9f
+
+	mov	%r9d, 20(%rsp)
+	test	%r9d, %r9d
+	jz	9f
+
+	/* Convert the on-stack pointer arguments to in-place
+	   from a 64-bit padded array into a 32-bit packed array.
+           Note that this is memory is callee owned.  */
+	xor	%ecx, %ecx
+1:	mov	24(%rsp, %rcx, 8), %edx
+	mov	%edx, 24(%rsp, %rcx, 4)
+	inc	%ecx
+	test	%edx, %edx
+	jnz	1b
+
+9:
+	/* Restore return address to the stack.  */
+	push	%rax
+	cfi_adjust_cfa_offset(8)
+	cfi_rel_offset(%rip, 0)
+
+	/* Load __environ for the env parameter.  */
+#ifdef PIC
+	mov	__environ@GOTPCREL(%rip), %edx
+	mov	(%rdx), %edx
+#else
+	mov	__environ(%rip), %edx
+#endif
+
+	/* Load argv parameter.  Note that path (esi) is already loaded.  */
+	lea	12(%rsp), %edi
+
+	DO_CALL (execve, 3)
+
+	/* All returns are errors.  */
+	SYSCALL_SET_ERRNO
+	or	$-1, %rax
+
+	/* Pop all of the extra stack space in one go.  */
+	ret	$24
+
+END(execl)
+
+libc_hidden_def (execl)
diff --git a/sysdeps/unix/sysv/linux/x86_64/x32/execle.S b/sysdeps/unix/sysv/linux/x86_64/x32/execle.S
new file mode 100644
index 0000000..c7de7e0
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/x32/execle.S
@@ -0,0 +1,87 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execle)
+	/* Move return address into a register.  */
+	pop	%rax
+	cfi_adjust_cfa_offset(-8)
+	cfi_register(%rip, %rax)
+
+	/* Save the arguments in registers.  Stop as soon as we detect
+	   the NULL terminator, as if we find one, we do not want to fall
+	   into the on-stack conversion loop.  Move the potential ENV
+	   parameter in place in EDX on each exit path.  */
+	sub	$24, %esp
+	cfi_adjust_cfa_offset(24)
+
+	mov	%edi, 4(%rsp)	/* argv[0] must be non-null.  */
+
+	mov	%edx, 8(%rsp)
+	test	%edx, %edx
+	mov	%ecx, %edx
+	jz	9f
+
+	mov	%ecx, 12(%rsp)
+	test	%ecx, %ecx
+	mov	%r8d, %edx
+	jz	9f
+
+	mov	%r8d, 16(%rsp)
+	test	%r8d, %r8d
+	mov	%r9d, %edx
+	jz	9f
+
+	mov	%r9d, 20(%rsp)
+	test	%r9d, %r9d
+	mov	24(%rsp), %edx
+	jz	9f
+
+	/* Convert the on-stack pointer arguments to in-place
+	   from a 64-bit padded array into a 32-bit packed array.
+           Note that this is memory is callee owned, and that this
+	   loop exits with the ENV parameter loaded in EDX.  */
+	xor	%ecx, %ecx
+	mov	24(%rsp, %rcx, 8), %edx
+1:	mov	%edx, 24(%rsp, %rcx, 4)
+	inc	%ecx
+	test	%edx, %edx
+	mov	24(%rsp, %rcx, 8), %edx
+	jnz	1b
+
+9:
+	/* Restore return address to the stack.  */
+	push	%rax
+	cfi_adjust_cfa_offset(8)
+	cfi_rel_offset(%rip, 0)
+
+	/* Load argv parameter.  Note that path (esi) is already loaded.  */
+	lea	12(%rsp), %edi
+
+	DO_CALL (execve, 3)
+
+	/* All returns are errors.  */
+	SYSCALL_SET_ERRNO
+	or	$-1, %rax
+
+	/* Pop all of the extra stack space in one go.  */
+	ret	$24
+
+END(execle)
+
+libc_hidden_def (execle)
diff --git a/sysdeps/unix/sysv/linux/x86_64/x32/execlp.S b/sysdeps/unix/sysv/linux/x86_64/x32/execlp.S
new file mode 100644
index 0000000..cad65f5
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/x32/execlp.S
@@ -0,0 +1,76 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execlp)
+	/* Move return address into a register.  */
+	pop	%rax
+	cfi_adjust_cfa_offset(-8)
+	cfi_register(%rip, %rax)
+
+	/* Save the arguments in registers.  Stop as soon as we detect
+	   the NULL terminator, as if we find one, we do not want to fall
+	   into the on-stack conversion loop.  */
+	sub	$24, %esp
+	cfi_adjust_cfa_offset(24)
+
+	mov	%edi, 4(%rsp)	/* argv[0] must be non-null.  */
+
+	mov	%edx, 8(%rsp)
+	test	%edx, %edx
+	jz	9f
+
+	mov	%ecx, 12(%rsp)
+	test	%ecx, %ecx
+	jz	9f
+
+	mov	%r8d, 16(%rsp)
+	test	%r8d, %r8d
+	jz	9f
+
+	mov	%r9d, 20(%rsp)
+	test	%r9d, %r9d
+	jz	9f
+
+	/* Convert the on-stack pointer arguments to in-place
+	   from a 64-bit padded array into a 32-bit packed array.
+           Note that this is memory is callee owned.  */
+	xor	%ecx, %ecx
+1:	mov	24(%rsp, %rcx, 8), %edx
+	mov	%edx, 24(%rsp, %rcx, 4)
+	inc	%ecx
+	test	%edx, %edx
+	jnz	1b
+
+9:
+	/* Restore return address to the stack.  */
+	push	%rax
+	cfi_adjust_cfa_offset(8)
+	cfi_rel_offset(%rip, 0)
+
+	/* Load argv parameter.  Note that path (esi) is already loaded.  */
+	lea	12(%rsp), %edi
+
+	call	HIDDEN_JUMPTARGET (execvp)
+
+	/* Pop all of the extra stack space in one go.  */
+	ret	$24
+
+END(execlp)
+
+libc_hidden_def (execlp)

http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=072dce81771f971f49f2480630842a2874a2c860

commit 072dce81771f971f49f2480630842a2874a2c860
Author: Richard Henderson <rth@twiddle.net>
Date:   Tue Feb 9 13:12:33 2016 +1100

    i386: Implement execl{,e,p} without double stack allocation

diff --git a/sysdeps/unix/sysv/linux/i386/execl.S b/sysdeps/unix/sysv/linux/i386/execl.S
new file mode 100644
index 0000000..047ef48
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/i386/execl.S
@@ -0,0 +1,39 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execl)
+	mov	4(%esp), %edx
+	lea	8(%esp), %eax
+
+	push	%eax			/* alignment padding */
+	cfi_adjust_cfa_offset(4)
+	push	%eax			/* create argv argument */
+	cfi_adjust_cfa_offset(4)
+	push	%edx			/* create path argument */
+	cfi_adjust_cfa_offset(4)
+
+	/* Let execv deal with pic vs non-pic loading of __environ.  */
+	call	HIDDEN_JUMPTARGET (execv)
+
+	add	$12, %esp
+	cfi_adjust_cfa_offset(-12)
+	ret
+END(execl)
+
+libc_hidden_def (execl)
diff --git a/sysdeps/unix/sysv/linux/i386/execle.S b/sysdeps/unix/sysv/linux/i386/execle.S
new file mode 100644
index 0000000..34cc7bc
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/i386/execle.S
@@ -0,0 +1,46 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execle)
+	lea	8(%esp), %eax	/* find argv array */
+
+	/* Find the env argument.  It is the array element after the argv
+	   NULL terminator, which cannot be located before argv[1].  */
+	mov	4(%eax), %edx
+	xor	%ecx, %ecx
+1:	inc	%ecx
+	test	%edx, %edx
+	mov	4(%eax, %ecx, 4), %edx
+	jnz	1b
+
+	push	%edx		/* create env argument */
+	cfi_adjust_cfa_offset(4)
+	push	%eax		/* create argv argument */
+	cfi_adjust_cfa_offset(4)
+	push	12(%esp)	/* copy path argument */
+	cfi_adjust_cfa_offset(4)
+
+	call	HIDDEN_JUMPTARGET (execve)
+
+	add	$12, %esp
+	cfi_adjust_cfa_offset(-12)
+	ret
+END(execle)
+
+libc_hidden_def (execle)
diff --git a/sysdeps/unix/sysv/linux/i386/execlp.S b/sysdeps/unix/sysv/linux/i386/execlp.S
new file mode 100644
index 0000000..d1c8806
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/i386/execlp.S
@@ -0,0 +1,4 @@
+#define execl		execlp
+#define execv		execvp
+#define __GI_execv	__GI_execvp
+#include "execl.S"

http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=447f711575e70c09fd883f28d86e175993025277

commit 447f711575e70c09fd883f28d86e175993025277
Author: Richard Henderson <rth@twiddle.net>
Date:   Tue Feb 9 12:53:17 2016 +1100

    x86_64: Implement execl{,e,p} without double stack allocation

diff --git a/include/unistd.h b/include/unistd.h
index 5152f64..21b8135 100644
--- a/include/unistd.h
+++ b/include/unistd.h
@@ -9,6 +9,7 @@ rtld_hidden_proto (_exit, __noreturn__)
 libc_hidden_proto (alarm)
 libc_hidden_proto (confstr)
 libc_hidden_proto (execl)
+libc_hidden_proto (execv)
 libc_hidden_proto (execle)
 libc_hidden_proto (execlp)
 libc_hidden_proto (execvp)
diff --git a/posix/execv.c b/posix/execv.c
index 16c0a02..faca14f 100644
--- a/posix/execv.c
+++ b/posix/execv.c
@@ -24,3 +24,4 @@ execv (const char *path, char *const argv[])
 {
   return __execve (path, argv, __environ);
 }
+libc_hidden_def (execv)
diff --git a/sysdeps/unix/sysv/linux/x86_64/64/execl.S b/sysdeps/unix/sysv/linux/x86_64/64/execl.S
new file mode 100644
index 0000000..29b4923
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/64/execl.S
@@ -0,0 +1,65 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execl)
+	/* Move return address into a register.  */
+	pop	%rax
+	cfi_adjust_cfa_offset(-8)
+	cfi_register(%rip, %rax)
+
+	/* Save the portions of the argv argument list in registers.  */
+	push	%r9
+	cfi_adjust_cfa_offset(8)
+	push	%r8
+	cfi_adjust_cfa_offset(8)
+	push	%rcx
+	cfi_adjust_cfa_offset(8)
+	push	%rdx
+	cfi_adjust_cfa_offset(8)
+	push	%rsi
+	cfi_adjust_cfa_offset(8)
+
+	/* Load the address of the argv array.  */
+	mov	%rsp, %rsi
+
+	/* Restore return address to the stack.  */
+	push	%rax
+	cfi_adjust_cfa_offset(8)
+	cfi_rel_offset(%rip, 0)
+
+	/* Load __environ for the env parameter.  */
+#ifdef PIC
+	mov	__environ@GOTPCREL(%rip), %rdx
+	mov	(%rdx), %rdx
+#else
+	mov	__environ(%rip), %rdx
+#endif
+
+	DO_CALL (execve, 3)
+
+	/* All returns are errors.  */
+	SYSCALL_SET_ERRNO
+	or	$-1, %rax
+
+	/* Pop all of the extra stack space in one go.  */
+	ret	$40
+
+END(execl)
+
+libc_hidden_def (execl)
diff --git a/sysdeps/unix/sysv/linux/x86_64/64/execle.S b/sysdeps/unix/sysv/linux/x86_64/64/execle.S
new file mode 100644
index 0000000..c2fc5c9
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/64/execle.S
@@ -0,0 +1,66 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execle)
+	/* Move return address into a register.  */
+	pop	%rax
+	cfi_adjust_cfa_offset(-8)
+	cfi_register(%rip, %rax)
+
+	/* Save the portions of the argv argument list in registers.  */
+	push	%r9
+	cfi_adjust_cfa_offset(8)
+	push	%r8
+	cfi_adjust_cfa_offset(8)
+	push	%rcx
+	cfi_adjust_cfa_offset(8)
+	push	%rdx
+	cfi_adjust_cfa_offset(8)
+	push	%rsi
+	cfi_adjust_cfa_offset(8)
+
+	/* Load the address of the argv array.  */
+	mov	%rsp, %rsi
+
+	/* Restore return address to the stack.  */
+	push	%rax
+	cfi_adjust_cfa_offset(8)
+	cfi_rel_offset(%rip, 0)
+
+	/* Find the env argument.  It is the array element after the argv
+	   NULL terminator, which cannot be located before argv[1].  */
+	lea	8(%rsi), %rax
+	mov	(%rax), %rdx
+1:	add	$8, %rax
+	test	%rdx, %rdx
+	mov	(%rax), %rdx
+	jnz	1b
+
+	DO_CALL (execve, 3)
+
+	/* All returns are errors.  */
+	SYSCALL_SET_ERRNO
+	or	$-1, %rax
+
+	/* Pop all of the extra stack space in one go.  */
+	ret	$40
+
+END(execle)
+
+libc_hidden_def (execle)
diff --git a/sysdeps/unix/sysv/linux/x86_64/64/execlp.S b/sysdeps/unix/sysv/linux/x86_64/64/execlp.S
new file mode 100644
index 0000000..caa0895
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/x86_64/64/execlp.S
@@ -0,0 +1,52 @@
+/* Copyright (C) 2016 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, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <sysdep.h>
+
+ENTRY(execlp)
+	/* Move return address into a register.  */
+	pop	%rax
+	cfi_adjust_cfa_offset(-8)
+	cfi_register(%rip, %rax)
+
+	/* Save the portions of the argv argument list in registers.  */
+	push	%r9
+	cfi_adjust_cfa_offset(8)
+	push	%r8
+	cfi_adjust_cfa_offset(8)
+	push	%rcx
+	cfi_adjust_cfa_offset(8)
+	push	%rdx
+	cfi_adjust_cfa_offset(8)
+	push	%rsi
+	cfi_adjust_cfa_offset(8)
+
+	/* Load the address of the argv array.  */
+	mov	%rsp, %rsi
+
+	/* Restore return address to the stack.  */
+	push	%rax
+	cfi_adjust_cfa_offset(8)
+	cfi_rel_offset(%rip, 0)
+
+	call	HIDDEN_JUMPTARGET (execvp)
+
+	/* Pop all of the extra stack space in one go.  */
+	ret	$40
+END(execlp)
+
+libc_hidden_def (execlp)

http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=f685eeedc6d7baf1bf822ef058e06bc1bcae4541

commit f685eeedc6d7baf1bf822ef058e06bc1bcae4541
Author: Richard Henderson <rth@twiddle.net>
Date:   Tue Feb 9 11:53:32 2016 +1100

    Move posix/execl files to sysdeps/
    
    This will allow them to be overridable.

diff --git a/posix/execl.c b/sysdeps/posix/execl.c
similarity index 100%
rename from posix/execl.c
rename to sysdeps/posix/execl.c
diff --git a/posix/execle.c b/sysdeps/posix/execle.c
similarity index 100%
rename from posix/execle.c
rename to sysdeps/posix/execle.c
diff --git a/posix/execlp.c b/sysdeps/posix/execlp.c
similarity index 100%
rename from posix/execlp.c
rename to sysdeps/posix/execlp.c

http://sourceware.org/git/gitweb.cgi?p=glibc.git;a=commitdiff;h=c4c95c53bbb6d41b56ad56921f1e14fa43b3e997

commit c4c95c53bbb6d41b56ad56921f1e14fa43b3e997
Author: Adhemerval Zanella <adhemerval dot zanella at linaro dot org>
Date:   Mon Feb 1 14:21:03 2016 -0200

    posix: Remove dynamic memory allocation from execl{e,p}
    
    GLIBC execl{e,p} implementation might use malloc if the total number of i
    arguments exceed initial assumption size (1024).  This might lead to
    issue in two situations:
    
    1. execl/execle is stated to be async-signal-safe by POSIX [1].  However
       if execl is used in a signal handler with a large argument set (that
       may call malloc internally) and the resulting call fails, it might
       lead malloc in the program in a bad state.
    
    2. If the functions are used in a vfork/clone(VFORK) situation it also
       might issue malloc internal bad state.
    
    This patch fixes it by using stack allocation instead.  It also fixes
    BZ#19534.
    
    Tested on x86_64.
    
    Changes from previous version:
    
    - Remove arbitrary limit on stack allocation for argument handling
      (it is arbitrary and does no impose any limit since it does not
      consider current stack size neither stack size limit).
    
    [1] http://pubs.opengroup.org/onlinepubs/9699919799/functions/V2_chap02.html
    
    	[BZ #19534]
    	* posix/execl.c (execl): Remove dynamic memory allocation.
    	* posix/execle.c (execle): Likewise.
    	* posix/execlp.c (execlp): Likewise.
    Message-Id: <1454343665-1706-2-git-send-email-adhemerval.zanella@linaro.org>

diff --git a/posix/execl.c b/posix/execl.c
index 102d19d..8b8a324 100644
--- a/posix/execl.c
+++ b/posix/execl.c
@@ -16,58 +16,31 @@
    <http://www.gnu.org/licenses/>.  */
 
 #include <unistd.h>
+#include <errno.h>
 #include <stdarg.h>
-#include <stddef.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include <stackinfo.h>
-
+#include <sys/param.h>
 
 /* Execute PATH with all arguments after PATH until
    a NULL pointer and environment from `environ'.  */
 int
 execl (const char *path, const char *arg, ...)
 {
-#define INITIAL_ARGV_MAX 1024
-  size_t argv_max = INITIAL_ARGV_MAX;
-  const char *initial_argv[INITIAL_ARGV_MAX];
-  const char **argv = initial_argv;
-  va_list args;
-
-  argv[0] = arg;
-
-  va_start (args, arg);
-  unsigned int i = 0;
-  while (argv[i++] != NULL)
-    {
-      if (i == argv_max)
-	{
-	  argv_max *= 2;
-	  const char **nptr = realloc (argv == initial_argv ? NULL : argv,
-				       argv_max * sizeof (const char *));
-	  if (nptr == NULL)
-	    {
-	      if (argv != initial_argv)
-		free (argv);
-	      va_end (args);
-	      return -1;
-	    }
-	  if (argv == initial_argv)
-	    /* We have to copy the already filled-in data ourselves.  */
-	    memcpy (nptr, argv, i * sizeof (const char *));
-
-	  argv = nptr;
-	}
-
-      argv[i] = va_arg (args, const char *);
-    }
-  va_end (args);
-
-  int ret = __execve (path, (char *const *) argv, __environ);
-  if (argv != initial_argv)
-    free (argv);
-
-  return ret;
+  int argc;
+  va_list ap;
+  va_start (ap, arg);
+  for (argc = 1; va_arg (ap, const char *); argc++)
+    continue;
+  va_end (ap);
+
+  int i;
+  char *argv[argc+1];
+  va_start (ap, arg);
+  argv[0] = (char*) arg;
+  for (i = 1; i < argc; i++)
+     argv[i] = va_arg (ap, char *);
+  argv[i] = NULL;
+  va_end (ap);
+
+  return __execve (path, argv, __environ);
 }
 libc_hidden_def (execl)
diff --git a/posix/execle.c b/posix/execle.c
index 8edc03a..1a0c9ee 100644
--- a/posix/execle.c
+++ b/posix/execle.c
@@ -17,57 +17,31 @@
 
 #include <unistd.h>
 #include <stdarg.h>
-#include <stddef.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include <stackinfo.h>
+#include <errno.h>
+#include <sys/param.h>
 
 /* Execute PATH with all arguments after PATH until a NULL pointer,
    and the argument after that for environment.  */
 int
 execle (const char *path, const char *arg, ...)
 {
-#define INITIAL_ARGV_MAX 1024
-  size_t argv_max = INITIAL_ARGV_MAX;
-  const char *initial_argv[INITIAL_ARGV_MAX];
-  const char **argv = initial_argv;
-  va_list args;
-  argv[0] = arg;
-
-  va_start (args, arg);
-  unsigned int i = 0;
-  while (argv[i++] != NULL)
-    {
-      if (i == argv_max)
-	{
-	  argv_max *= 2;
-	  const char **nptr = realloc (argv == initial_argv ? NULL : argv,
-				       argv_max * sizeof (const char *));
-	  if (nptr == NULL)
-	    {
-	      if (argv != initial_argv)
-		free (argv);
-	      va_end (args);
-	      return -1;
-	    }
-	  if (argv == initial_argv)
-	    /* We have to copy the already filled-in data ourselves.  */
-	    memcpy (nptr, argv, i * sizeof (const char *));
-
-	  argv = nptr;
-	}
-
-      argv[i] = va_arg (args, const char *);
-    }
-
-  const char *const *envp = va_arg (args, const char *const *);
-  va_end (args);
-
-  int ret = __execve (path, (char *const *) argv, (char *const *) envp);
-  if (argv != initial_argv)
-    free (argv);
-
-  return ret;
+  int argc;
+  va_list ap;
+  va_start (ap, arg);
+  for (argc = 1; va_arg (ap, const char *); argc++)
+    continue;
+  va_end (ap);
+
+  int i;
+  char *argv[argc+1];
+  char **envp;
+  va_start (ap, arg);
+  argv[0] = (char*) arg;
+  for (i = 1; i < argc; i++)
+     argv[i] = va_arg (ap, char *);
+  envp = va_arg (ap, char **);
+  va_end (ap);
+
+  return __execve (path, argv, envp);
 }
 libc_hidden_def (execle)
diff --git a/posix/execlp.c b/posix/execlp.c
index 6700994..a0e1859 100644
--- a/posix/execlp.c
+++ b/posix/execlp.c
@@ -17,11 +17,8 @@
 
 #include <unistd.h>
 #include <stdarg.h>
-#include <stddef.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include <stackinfo.h>
+#include <errno.h>
+#include <sys/param.h>
 
 /* Execute FILE, searching in the `PATH' environment variable if
    it contains no slashes, with all arguments after FILE until a
@@ -29,45 +26,22 @@
 int
 execlp (const char *file, const char *arg, ...)
 {
-#define INITIAL_ARGV_MAX 1024
-  size_t argv_max = INITIAL_ARGV_MAX;
-  const char *initial_argv[INITIAL_ARGV_MAX];
-  const char **argv = initial_argv;
-  va_list args;
-
-  argv[0] = arg;
-
-  va_start (args, arg);
-  unsigned int i = 0;
-  while (argv[i++] != NULL)
-    {
-      if (i == argv_max)
-	{
-	  argv_max *= 2;
-	  const char **nptr = realloc (argv == initial_argv ? NULL : argv,
-				       argv_max * sizeof (const char *));
-	  if (nptr == NULL)
-	    {
-	      if (argv != initial_argv)
-		free (argv);
-	      va_end (args);
-	      return -1;
-	    }
-	  if (argv == initial_argv)
-	    /* We have to copy the already filled-in data ourselves.  */
-	    memcpy (nptr, argv, i * sizeof (const char *));
-
-	  argv = nptr;
-	}
-
-      argv[i] = va_arg (args, const char *);
-    }
-  va_end (args);
-
-  int ret = execvp (file, (char *const *) argv);
-  if (argv != initial_argv)
-    free (argv);
-
-  return ret;
+  int argc;
+  va_list ap;
+  va_start (ap, arg);
+  for (argc = 1; va_arg (ap, const char *); argc++)
+    continue;
+  va_end (ap);
+
+  int i;
+  char *argv[argc+1];
+  va_start (ap, arg);
+  argv[0] = (char*) arg;
+  for (i = 1; i < argc; i++)
+     argv[i] = va_arg (ap, char *);
+  argv[i] = NULL;
+  va_end (ap);
+
+  return __execvpe (file, argv, __environ);
 }
 libc_hidden_def (execlp)

-----------------------------------------------------------------------


hooks/post-receive
-- 
GNU C Library master sources


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]