63 lines
		
	
	
		
			1.6 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			63 lines
		
	
	
		
			1.6 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
/* The kernel call implemented in this file:
 | 
						|
 *   m_type:	SYS_SYSCTL
 | 
						|
 *
 | 
						|
 * The parameters for this kernel call are:
 | 
						|
 *  	SYSCTL_CODE	request
 | 
						|
 * and then request-specific arguments in SYSCTL_ARG1 and SYSCTL_ARG2.
 | 
						|
 */
 | 
						|
 | 
						|
#include "../system.h"
 | 
						|
#include "../vm.h"
 | 
						|
 | 
						|
 | 
						|
/*===========================================================================*
 | 
						|
 *			        do_sysctl				     *
 | 
						|
 *===========================================================================*/
 | 
						|
PUBLIC int do_sysctl(m_ptr)
 | 
						|
register message *m_ptr;	/* pointer to request message */
 | 
						|
{
 | 
						|
  phys_bytes ph;
 | 
						|
  vir_bytes len, buf;
 | 
						|
  static char mybuf[DIAG_BUFSIZE];
 | 
						|
  struct proc *caller, *target;
 | 
						|
  int s, i, proc_nr;
 | 
						|
 | 
						|
  caller = proc_addr(who_p);
 | 
						|
 | 
						|
  switch (m_ptr->SYSCTL_CODE) {
 | 
						|
    case SYSCTL_CODE_DIAG:
 | 
						|
        buf = (vir_bytes) m_ptr->SYSCTL_ARG1;
 | 
						|
        len = (vir_bytes) m_ptr->SYSCTL_ARG2;
 | 
						|
	if(len < 1 || len > DIAG_BUFSIZE) {
 | 
						|
		kprintf("do_sysctl: diag for %d: len %d out of range\n",
 | 
						|
			caller->p_endpoint, len);
 | 
						|
		return EINVAL;
 | 
						|
	}
 | 
						|
	if((ph=umap_local(caller, D, buf, len)) == 0)
 | 
						|
		return EFAULT;
 | 
						|
	CHECKRANGE_OR_SUSPEND(caller, ph, len, 1);
 | 
						|
	if((s=data_copy(who_e, buf, SYSTEM, (vir_bytes) mybuf, len)) != OK) {
 | 
						|
		kprintf("do_sysctl: diag for %d: len %d: copy failed: %d\n",
 | 
						|
			caller->p_endpoint, len, s);
 | 
						|
		return s;
 | 
						|
	}
 | 
						|
	for(i = 0; i < len; i++)
 | 
						|
		kputc(mybuf[i]);
 | 
						|
	kputc(END_OF_KMESS);
 | 
						|
	return OK;
 | 
						|
    case SYSCTL_CODE_STACKTRACE:
 | 
						|
	if(!isokendpt(m_ptr->SYSCTL_ARG2, &proc_nr))
 | 
						|
		return EINVAL;
 | 
						|
	proc_stacktrace(proc_addr(proc_nr));
 | 
						|
	return OK;
 | 
						|
    default:
 | 
						|
	kprintf("do_sysctl: invalid request %d\n", m_ptr->SYSCTL_CODE);
 | 
						|
        return(EINVAL);
 | 
						|
  }
 | 
						|
 | 
						|
  minix_panic("do_sysctl: can't happen", NO_NUM);
 | 
						|
 | 
						|
  return(OK);
 | 
						|
}
 | 
						|
 |