Bug 72998 - [kernel] [patch] set_mcontext() change syscalls parameters on sparc64
Summary: [kernel] [patch] set_mcontext() change syscalls parameters on sparc64
Status: Closed FIXED
Alias: None
Product: Base System
Classification: Unclassified
Component: sparc64 (show other bugs)
Version: 5.3-BETA7
Hardware: Any Any
: Normal Affects Only Me
Assignee: freebsd-sparc64 (Nobody)
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2004-10-22 12:50 UTC by bel
Modified: 2008-08-28 19:30 UTC (History)
0 users

See Also:


Attachments
sparc64_trap.patch (411 bytes, patch)
2004-10-22 12:50 UTC, bel
no flags Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description bel 2004-10-22 12:50:12 UTC
	Some syscalls using set_mcontext can sneakily change
parameters and later when those syscalls references parameters,
they will wrongly use register values in mcontext_t.

	This problem is critical for thread related syscalls!

Fix: Simple patch. See also amd64/amd64/trap.c revision 1.278.

<http://www.freebsd.org/cgi/cvsweb.cgi/src/sys/amd64/amd64/trap.c.diff?r1=1.277&r2=1.278>
How-To-Repeat: 
	Use following changes in kernel:

--- debug.patch begins here ---
--- sys/kern/kern_kse.c.orig	Fri Oct 22 14:47:07 2004
+++ sys/kern/kern_kse.c	Fri Oct 22 14:46:13 2004
@@ -140,8 +140,12 @@ kse_switchin(struct thread *td, struct k
 	if (!error && (uap->flags & KSE_SWITCHIN_SETTMBX))
 		error = (suword(&ku->ku_mailbox->km_curthread,
 			 (long)uap->tmbx) != 0 ? EINVAL : 0);
+	TR2("thread_schedule_upcall: before set_mcontext: tmbx %p flags %d",
+	     uap->tmbx, uap->flags);
 	if (!error)
 		error = set_mcontext(td, &tmbx.tm_context.uc_mcontext);
+	TR2("thread_schedule_upcall: after set_mcontext: tmbx %p flags %d",
+	     uap->tmbx, uap->flags);
 	if (!error) {
 		suword32(&uap->tmbx->tm_lwp, td->td_tid);
 		if (uap->flags & KSE_SWITCHIN_SETTMBX) {
--- sys/sparc64/conf/GENERIC.orig	Wed Sep 22 23:23:39 2004
+++ sys/sparc64/conf/GENERIC	Fri Oct 22 15:00:49 2004
@@ -201,3 +201,7 @@
 device		firewire	# FireWire bus code
 device		sbp		# SCSI over FireWire (Requires scbus and da)
 device		fwe		# Ethernet over FireWire (non-standard!)
+
+options		KDB		#Enable kernel debugger support
+options		DDB		#Enable the kernel debugger
+options		GDB		#Support remote GDB
+options		KTR
+options		KTR_COMPILE=(KTR_GEN|KTR_SMP|KTR_TRAP|KTR_INTR|KTR_SIG|KTR_PROC|KTR_SYSC)
+options		KTR_ENTRIES=8192
--- debug.patch ends here ---

	Run any simple threated program compiled with libkse. For example:

--- hello_d.c begins here ---
/****************************************************************************
 *
 * Simple diff mode test.
 *
 * $FreeBSD: src/lib/libpthread/test/hello_d.c,v 1.1 2000/04/24 21:07:37 jasone Exp $
 *
 ****************************************************************************/

#include <stdio.h>
#include <string.h>
#include <pthread.h>

extern int _libkse_debug;

void *
entry(void * a_arg)
{
	char *str = NULL;
	fprintf(stderr, "Hello world\n");
#if 0
	*str = 'a';
#endif

	return NULL;
}

int
main()
{
	pthread_t thread;
	int error;
	pthread_attr_t attr;
	int scope;

/*
	_libkse_debug = 1;
 */
	error = pthread_attr_init(&attr);
	if (error)
		fprintf(stderr, "Error in pthread_attr_init(): %s\n",
			strerror(error));

	error = pthread_attr_getscope(&attr, &scope);
	if (error)
		fprintf(stderr, "Error in pthread_attr_getscope(): %s\n",
			strerror(error));

	printf("Default scope: %d\n", scope);
#if 1
	scope |= PTHREAD_SCOPE_SYSTEM;
#endif
	printf("Set scope: %d\n", scope);

	error = pthread_attr_setscope(&attr, scope);
	if (error)
		fprintf(stderr, "Error in pthread_attr_setscope(): %s\n",
			strerror(error));

	error = pthread_create(&thread, &attr, entry, NULL);
	if (error)
		fprintf(stderr, "Error in pthread_create(): %s\n",
			strerror(error));

	error = pthread_join(thread, NULL);
	if (error)
		fprintf(stderr, "Error in pthread_join(): %s\n",
			strerror(error));

	error = pthread_attr_destroy(&attr);
	if (error)
		fprintf(stderr, "Error in pthread_attr_destroy(): %s\n",
			strerror(error));

	return 0;
}
--- hello_d.c ends here ---

	Go to kernel debugger by pressing Control-Alt-Esc and "show ktr".
Compare arguments before and after set_mcontext.
Comment 1 Pietro Cerutti freebsd_committer freebsd_triage 2008-06-10 01:49:28 UTC
State Changed
From-To: open->closed

It has been fixed on revision 1.9 of src/sys/sparc64/sparc64/trap.c. 
Thanks!
Comment 2 dfilter service freebsd_committer freebsd_triage 2008-08-24 21:02:50 UTC
marius      2008-08-24 20:02:18 UTC

  FreeBSD src repository

  Modified files:
    sys/sparc64/sparc64  trap.c 
  Log:
  SVN rev 182119 on 2008-08-24 20:02:18Z by marius
  
  MFamd64: r133413
  
  In syscall, always make a copy of parameters from trapframe, this
  becauses some syscalls using set_mcontext can sneakily change
  parameters and later when those syscalls references parameters,
  they will wrongly use register values in mcontext_t.
  
  PR:             72998
  MFC after:      3 days
  
  Revision  Changes    Path
  1.92      +6 -9      src/sys/sparc64/sparc64/trap.c
_______________________________________________
cvs-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/cvs-all
To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"
Comment 3 dfilter service freebsd_committer freebsd_triage 2008-08-28 19:24:46 UTC
marius      2008-08-28 18:24:24 UTC

  FreeBSD src repository

  Modified files:        (Branch: RELENG_7)
    sys/sparc64/sparc64  trap.c 
  Log:
  SVN rev 182389 on 2008-08-28 18:24:24Z by marius
  
  MFC: r182119
  MFamd64: r133413
  
  In syscall, always make a copy of parameters from trapframe, this
  becauses some syscalls using set_mcontext can sneakily change
  parameters and later when those syscalls references parameters,
  they will wrongly use register values in mcontext_t.
  
  PR:             72998
  
  Revision  Changes    Path
  1.88.2.3  +6 -9      src/sys/sparc64/sparc64/trap.c
_______________________________________________
cvs-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/cvs-all
To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"
Comment 4 dfilter service freebsd_committer freebsd_triage 2008-08-28 19:25:02 UTC
marius      2008-08-28 18:24:27 UTC

  FreeBSD src repository

  Modified files:        (Branch: RELENG_6)
    sys/sparc64/sparc64  trap.c 
  Log:
  SVN rev 182390 on 2008-08-28 18:24:27Z by marius
  
  MFC: r182119
  MFamd64: r133413
  
  In syscall, always make a copy of parameters from trapframe, this
  becauses some syscalls using set_mcontext can sneakily change
  parameters and later when those syscalls references parameters,
  they will wrongly use register values in mcontext_t.
  
  PR:             72998
  
  Revision  Changes    Path
  1.74.2.4  +6 -9      src/sys/sparc64/sparc64/trap.c
_______________________________________________
cvs-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/cvs-all
To unsubscribe, send any mail to "cvs-all-unsubscribe@freebsd.org"