Beispiel #1
0
void start_thread(struct pt_regs *regs, unsigned long eip, unsigned long esp)
{
	PT_REGS_IP(regs) = eip;
	PT_REGS_SP(regs) = esp;
	current->ptrace &= ~PT_DTRACE;
#ifdef SUBARCH_EXECVE1
	SUBARCH_EXECVE1(regs->regs);
#endif
}
Beispiel #2
0
void start_thread_tt(struct pt_regs *regs, unsigned long eip, 
		     unsigned long esp)
{
	set_fs(USER_DS);
	flush_tlb_mm(current->mm);
	PT_REGS_IP(regs) = eip;
	PT_REGS_SP(regs) = esp;
	PT_FIX_EXEC_STACK(esp);
}
Beispiel #3
0
int setup_signal_stack_si(unsigned long stack_top, int sig,
			  struct k_sigaction *ka, struct pt_regs *regs,
			  siginfo_t *info, sigset_t *mask)
{
	struct rt_sigframe __user *frame;
	void __user *restorer;
	unsigned long save_sp = PT_REGS_SP(regs);
	int err = 0;

	stack_top &= -8UL;
	frame = (struct rt_sigframe __user *) stack_top - 1;
	if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
		return 1;

	restorer = frame->retcode;
	if(ka->sa.sa_flags & SA_RESTORER)
		restorer = ka->sa.sa_restorer;

	/* See comment above about why this is here */
	PT_REGS_SP(regs) = (unsigned long) frame;

	err |= __put_user(restorer, &frame->pretcode);
	err |= __put_user(sig, &frame->sig);
	err |= __put_user(&frame->info, &frame->pinfo);
	err |= __put_user(&frame->uc, &frame->puc);
	err |= copy_siginfo_to_user(&frame->info, info);
	err |= copy_ucontext_to_user(&frame->uc, &frame->fpstate, mask,
				     save_sp);

	/*
	 * This is movl $,%eax ; int $0x80
	 *
	 * WE DO NOT USE IT ANY MORE! It's only left here for historical
	 * reasons and because gdb uses it as a signature to notice
	 * signal handler stack frames.
	 */
	err |= __put_user(0xb8, (char __user *)(frame->retcode+0));
	err |= __put_user(__NR_rt_sigreturn, (int __user *)(frame->retcode+1));
	err |= __put_user(0x80cd, (short __user *)(frame->retcode+5));

	if(err)
		goto err;

	PT_REGS_IP(regs) = (unsigned long) ka->sa.sa_handler;
	PT_REGS_EAX(regs) = (unsigned long) sig;
	PT_REGS_EDX(regs) = (unsigned long) &frame->info;
	PT_REGS_ECX(regs) = (unsigned long) &frame->uc;

	if ((current->ptrace & PT_DTRACE) && (current->ptrace & PT_PTRACED))
		ptrace_notify(SIGTRAP);
	return 0;

err:
	PT_REGS_SP(regs) = save_sp;
	return err;
}
static int kern_do_signal(struct pt_regs *regs)
{
	struct k_sigaction ka_copy;
	siginfo_t info;
	sigset_t *oldset;
	int sig, handled_sig = 0;

	if (test_thread_flag(TIF_RESTORE_SIGMASK))
		oldset = &current->saved_sigmask;
	else
		oldset = &current->blocked;

	while ((sig = get_signal_to_deliver(&info, &ka_copy, regs, NULL)) > 0) {
		handled_sig = 1;
		/* Whee!  Actually deliver the signal.  */
		handle_signal(regs, sig, &ka_copy, &info);
	}

	/* Did we come from a system call? */
	if (!handled_sig && (PT_REGS_SYSCALL_NR(regs) >= 0)) {
		/* Restart the system call - no handlers present */
		switch (PT_REGS_SYSCALL_RET(regs)) {
		case -ERESTARTNOHAND:
		case -ERESTARTSYS:
		case -ERESTARTNOINTR:
			PT_REGS_ORIG_SYSCALL(regs) = PT_REGS_SYSCALL_NR(regs);
			PT_REGS_RESTART_SYSCALL(regs);
			break;
		case -ERESTART_RESTARTBLOCK:
			PT_REGS_ORIG_SYSCALL(regs) = __NR_restart_syscall;
			PT_REGS_RESTART_SYSCALL(regs);
			break;
		}
	}

	/*
	 * This closes a way to execute a system call on the host.  If
	 * you set a breakpoint on a system call instruction and singlestep
	 * from it, the tracing thread used to PTRACE_SINGLESTEP the process
	 * rather than PTRACE_SYSCALL it, allowing the system call to execute
	 * on the host.  The tracing thread will check this flag and
	 * PTRACE_SYSCALL if necessary.
	 */
	if (current->ptrace & PT_DTRACE)
		current->thread.singlestep_syscall =
			is_syscall(PT_REGS_IP(&current->thread.regs));

	/*
	 * if there's no signal to deliver, we just put the saved sigmask
	 * back
	 */
	if (!handled_sig)
		restore_saved_sigmask();
	return handled_sig;
}
static int kern_do_signal(struct pt_regs *regs)
{
	struct k_sigaction ka_copy;
	siginfo_t info;
	sigset_t *oldset;
	int sig, handled_sig = 0;

	if (test_thread_flag(TIF_RESTORE_SIGMASK))
		oldset = &current->saved_sigmask;
	else
		oldset = &current->blocked;

	while ((sig = get_signal_to_deliver(&info, &ka_copy, regs, NULL)) > 0) {
		handled_sig = 1;
		
		if (!handle_signal(regs, sig, &ka_copy, &info, oldset)) {
			if (test_thread_flag(TIF_RESTORE_SIGMASK))
				clear_thread_flag(TIF_RESTORE_SIGMASK);
			break;
		}
	}

	
	if (!handled_sig && (PT_REGS_SYSCALL_NR(regs) >= 0)) {
		
		switch (PT_REGS_SYSCALL_RET(regs)) {
		case -ERESTARTNOHAND:
		case -ERESTARTSYS:
		case -ERESTARTNOINTR:
			PT_REGS_ORIG_SYSCALL(regs) = PT_REGS_SYSCALL_NR(regs);
			PT_REGS_RESTART_SYSCALL(regs);
			break;
		case -ERESTART_RESTARTBLOCK:
			PT_REGS_ORIG_SYSCALL(regs) = __NR_restart_syscall;
			PT_REGS_RESTART_SYSCALL(regs);
			break;
		}
	}

	if (current->ptrace & PT_DTRACE)
		current->thread.singlestep_syscall =
			is_syscall(PT_REGS_IP(&current->thread.regs));

	if (!handled_sig && test_thread_flag(TIF_RESTORE_SIGMASK)) {
		clear_thread_flag(TIF_RESTORE_SIGMASK);
		sigprocmask(SIG_SETMASK, &current->saved_sigmask, NULL);
	}
	return handled_sig;
}
Beispiel #6
0
int setup_signal_stack_sc(unsigned long stack_top, int sig,
			  struct k_sigaction *ka, struct pt_regs *regs,
			  sigset_t *mask)
{
	struct sigframe __user *frame;
	void *restorer;
	int err = 0;

	stack_top &= -8UL;
	frame = (struct sigframe *) stack_top - 1;
	if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
		return 1;

	restorer = (void *) frame->retcode;
	if(ka->sa.sa_flags & SA_RESTORER)
		restorer = ka->sa.sa_restorer;

	err |= __put_user(restorer, &frame->pretcode);
	err |= __put_user(sig, &frame->sig);
	err |= copy_sc_to_user(&frame->sc, NULL, regs);
	err |= __put_user(mask->sig[0], &frame->sc.oldmask);
	if (_NSIG_WORDS > 1)
		err |= __copy_to_user(&frame->extramask, &mask->sig[1],
				      sizeof(frame->extramask));

	/*
	 * This is popl %eax ; movl $,%eax ; int $0x80
	 *
	 * WE DO NOT USE IT ANY MORE! It's only left here for historical
	 * reasons and because gdb uses it as a signature to notice
	 * signal handler stack frames.
	 */
	err |= __put_user(0xb858, (short __user *)(frame->retcode+0));
	err |= __put_user(__NR_sigreturn, (int __user *)(frame->retcode+2));
	err |= __put_user(0x80cd, (short __user *)(frame->retcode+6));

	if(err)
		return(err);

	PT_REGS_SP(regs) = (unsigned long) frame;
	PT_REGS_IP(regs) = (unsigned long) ka->sa.sa_handler;
	PT_REGS_EAX(regs) = (unsigned long) sig;
	PT_REGS_EDX(regs) = (unsigned long) 0;
	PT_REGS_ECX(regs) = (unsigned long) 0;

	if ((current->ptrace & PT_DTRACE) && (current->ptrace & PT_PTRACED))
		ptrace_notify(SIGTRAP);
	return(0);
}
Beispiel #7
0
static int kern_do_signal(struct pt_regs *regs, sigset_t *oldset, int error)
{
	siginfo_t info;
	struct k_sigaction *ka;
	int err, sig;

	if (!oldset)
		oldset = &current->blocked;

	sig = get_signal_to_deliver(&info, regs, NULL);
	if(sig == 0)
		return(0);

	/* Whee!  Actually deliver the signal.  */
	ka = &current->sig->action[sig -1 ];
	err = handle_signal(regs, sig, ka, &info, oldset, error);
	if(!err) return(1);

	/* Did we come from a system call? */
	if(PT_REGS_SYSCALL_NR(regs) >= 0){
		/* Restart the system call - no handlers present */
		if(PT_REGS_SYSCALL_RET(regs) == -ERESTARTNOHAND ||
		   PT_REGS_SYSCALL_RET(regs) == -ERESTARTSYS ||
		   PT_REGS_SYSCALL_RET(regs) == -ERESTARTNOINTR){
			PT_REGS_ORIG_SYSCALL(regs) = PT_REGS_SYSCALL_NR(regs);
			PT_REGS_RESTART_SYSCALL(regs);
		}
		else if(PT_REGS_SYSCALL_RET(regs) == -ERESTART_RESTARTBLOCK){
			PT_REGS_SYSCALL_RET(regs) = __NR_restart_syscall;
			PT_REGS_RESTART_SYSCALL(regs);
 		}
	}

	/* This closes a way to execute a system call on the host.  If
	 * you set a breakpoint on a system call instruction and singlestep
	 * from it, the tracing thread used to PTRACE_SINGLESTEP the process
	 * rather than PTRACE_SYSCALL it, allowing the system call to execute
	 * on the host.  The tracing thread will check this flag and 
	 * PTRACE_SYSCALL if necessary.
	 */
	if((current->ptrace & PT_DTRACE) && 
	   is_syscall(PT_REGS_IP(&current->thread.regs)))
 		(void) CHOOSE_MODE(current->thread.mode.tt.singlestep_syscall = 1, 0);
	return(0);
}
Beispiel #8
0
int setup_signal_stack_sc(unsigned long stack_top, int sig, 
			  struct k_sigaction *ka, struct pt_regs *regs,
			  sigset_t *mask)
{
	struct frame_common *frame = &signal_frame_sc_sr.common;
	void *restorer;
	void *user_sc;
	int sig_size = (_NSIG_WORDS - 1) * sizeof(unsigned long);
	unsigned long sigs, sr;
	unsigned long start = stack_top - frame->len - sig_size;

	restorer = NULL;
	if(ka->sa.sa_flags & SA_RESTORER)
		restorer = ka->sa.sa_restorer;

	user_sc = (void *) (start + signal_frame_sc_sr.sc_index);
	if(restorer == NULL){
		frame = &signal_frame_sc.common;
		user_sc = (void *) (start + signal_frame_sc.sc_index);
		sr = (unsigned long) frame->data;
		sr += frame->sr_index;
		sr = *((unsigned long *) sr);
		restorer = ((void (*)(void)) sr);
	}

	sigs = start + frame->len;
	if(copy_to_user((void *) start, frame->data, frame->len) ||
	   copy_to_user((void *) (start + frame->sig_index), &sig, 
			sizeof(sig)) ||
	   copy_sc_to_user(user_sc, NULL, regs, 
			   &signal_frame_sc.common.arch) ||
	   copy_to_user(sc_sigmask(user_sc), mask, sizeof(mask->sig[0])) ||
	   copy_to_user((void *) sigs, &mask->sig[1], sig_size) ||
	   copy_restorer(restorer, start, frame->sr_index, frame->sr_relative))
		return(1);

	PT_REGS_IP(regs) = (unsigned long) ka->sa.sa_handler;
	PT_REGS_SP(regs) = start + frame->sp_index;

	return(0);
}
Beispiel #9
0
void __show_regs(struct pt_regs *regs)
{
	printk("\n");
	print_modules();
	printk(KERN_INFO "Pid: %d, comm: %.20s %s %s\n", task_pid_nr(current),
		current->comm, print_tainted(), init_utsname()->release);
	printk(KERN_INFO "RIP: %04lx:[<%016lx>]\n", PT_REGS_CS(regs) & 0xffff,
	       PT_REGS_IP(regs));
	printk(KERN_INFO "RSP: %016lx  EFLAGS: %08lx\n", PT_REGS_SP(regs),
	       PT_REGS_EFLAGS(regs));
	printk(KERN_INFO "RAX: %016lx RBX: %016lx RCX: %016lx\n",
	       PT_REGS_AX(regs), PT_REGS_BX(regs), PT_REGS_CX(regs));
	printk(KERN_INFO "RDX: %016lx RSI: %016lx RDI: %016lx\n",
	       PT_REGS_DX(regs), PT_REGS_SI(regs), PT_REGS_DI(regs));
	printk(KERN_INFO "RBP: %016lx R08: %016lx R09: %016lx\n",
	       PT_REGS_BP(regs), PT_REGS_R8(regs), PT_REGS_R9(regs));
	printk(KERN_INFO "R10: %016lx R11: %016lx R12: %016lx\n",
	       PT_REGS_R10(regs), PT_REGS_R11(regs), PT_REGS_R12(regs));
	printk(KERN_INFO "R13: %016lx R14: %016lx R15: %016lx\n",
	       PT_REGS_R13(regs), PT_REGS_R14(regs), PT_REGS_R15(regs));
}
Beispiel #10
0
int setup_signal_stack_si(unsigned long stack_top, int sig, 
			  struct k_sigaction *ka, struct pt_regs *regs,
			  siginfo_t *info, sigset_t *mask)
{
	unsigned long start;
	void *restorer;
	void *sip, *ucp, *fp;

	start = stack_top - signal_frame_si.common.len;
	sip = (void *) (start + signal_frame_si.si_index);
	ucp = (void *) (start + signal_frame_si.uc_index);
	fp = (void *) (((unsigned long) ucp) + sizeof(struct ucontext));

	restorer = NULL;
	if(ka->sa.sa_flags & SA_RESTORER)
		restorer = ka->sa.sa_restorer;

	if(restorer == NULL)
		panic("setup_signal_stack_si - no restorer");

	if(copy_to_user((void *) start, signal_frame_si.common.data,
			signal_frame_si.common.len) ||
	   copy_to_user((void *) (start + signal_frame_si.common.sig_index), 
			&sig, sizeof(sig)) ||
	   copy_siginfo_to_user(sip, info) ||
	   copy_to_user((void *) (start + signal_frame_si.sip_index), &sip,
			sizeof(sip)) ||
	   copy_ucontext_to_user(ucp, fp, mask, PT_REGS_SP(regs)) ||
	   copy_to_user((void *) (start + signal_frame_si.ucp_index), &ucp,
			sizeof(ucp)) ||
	   copy_restorer(restorer, start, signal_frame_si.common.sr_index,
			 signal_frame_si.common.sr_relative))
		return(1);
	
	PT_REGS_IP(regs) = (unsigned long) ka->sa.sa_handler;
	PT_REGS_SP(regs) = start + signal_frame_si.common.sp_index;
	return(0);
}
Beispiel #11
0
void start_thread(struct pt_regs *regs, unsigned long eip, unsigned long esp)
{
	PT_REGS_IP(regs) = eip;
	PT_REGS_SP(regs) = esp;
}
Beispiel #12
0
int setup_signal_stack_sc(unsigned long stack_top, int sig,
			  struct k_sigaction *ka, struct pt_regs *regs,
			  sigset_t *mask)
{
	struct sigframe __user *frame;
	void __user *restorer;
	unsigned long save_sp = PT_REGS_SP(regs);
	int err = 0;

	/* This is the same calculation as i386 - ((sp + 4) & 15) == 0 */
	stack_top = ((stack_top + 4) & -16UL) - 4;
	frame = (struct sigframe __user *) stack_top - 1;
	if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
		return 1;

	restorer = frame->retcode;
	if(ka->sa.sa_flags & SA_RESTORER)
		restorer = ka->sa.sa_restorer;

	/* Update SP now because the page fault handler refuses to extend
	 * the stack if the faulting address is too far below the current
	 * SP, which frame now certainly is.  If there's an error, the original
	 * value is restored on the way out.
	 * When writing the sigcontext to the stack, we have to write the
	 * original value, so that's passed to copy_sc_to_user, which does
	 * the right thing with it.
	 */
	PT_REGS_SP(regs) = (unsigned long) frame;

	err |= __put_user(restorer, &frame->pretcode);
	err |= __put_user(sig, &frame->sig);
	err |= copy_sc_to_user(&frame->sc, NULL, regs, save_sp);
	err |= __put_user(mask->sig[0], &frame->sc.oldmask);
	if (_NSIG_WORDS > 1)
		err |= __copy_to_user(&frame->extramask, &mask->sig[1],
				      sizeof(frame->extramask));

	/*
	 * This is popl %eax ; movl $,%eax ; int $0x80
	 *
	 * WE DO NOT USE IT ANY MORE! It's only left here for historical
	 * reasons and because gdb uses it as a signature to notice
	 * signal handler stack frames.
	 */
	err |= __put_user(0xb858, (short __user *)(frame->retcode+0));
	err |= __put_user(__NR_sigreturn, (int __user *)(frame->retcode+2));
	err |= __put_user(0x80cd, (short __user *)(frame->retcode+6));

	if(err)
		goto err;

	PT_REGS_SP(regs) = (unsigned long) frame;
	PT_REGS_IP(regs) = (unsigned long) ka->sa.sa_handler;
	PT_REGS_EAX(regs) = (unsigned long) sig;
	PT_REGS_EDX(regs) = (unsigned long) 0;
	PT_REGS_ECX(regs) = (unsigned long) 0;

	if ((current->ptrace & PT_DTRACE) && (current->ptrace & PT_PTRACED))
		ptrace_notify(SIGTRAP);
	return 0;

err:
	PT_REGS_SP(regs) = save_sp;
	return err;
}