The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/kernel/system/do_getinfo.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /* The kernel call implemented in this file:
    2  *   m_type:    SYS_GETINFO
    3  *
    4  * The parameters for this kernel call are:
    5  *    m1_i3:    I_REQUEST       (what info to get)      
    6  *    m1_p1:    I_VAL_PTR       (where to put it)       
    7  *    m1_i1:    I_VAL_LEN       (maximum length expected, optional)     
    8  *    m1_p2:    I_VAL_PTR2      (second, optional pointer)      
    9  *    m1_i2:    I_VAL_LEN2      (second length or process nr)   
   10  */
   11 
   12 #include "../system.h"
   13 
   14 static unsigned long bios_buf[1024];    /* 4K, what about alignment */
   15 static vir_bytes bios_buf_vir, bios_buf_len;
   16 
   17 #if USE_GETINFO
   18 
   19 /*===========================================================================*
   20  *                              do_getinfo                                   *
   21  *===========================================================================*/
   22 PUBLIC int do_getinfo(m_ptr)
   23 register message *m_ptr;        /* pointer to request message */
   24 {
   25 /* Request system information to be copied to caller's address space. This
   26  * call simply copies entire data structures to the caller.
   27  */
   28   size_t length;
   29   phys_bytes src_phys; 
   30   phys_bytes dst_phys; 
   31   int proc_nr, nr;
   32 
   33   /* Set source address and length based on request type. */
   34   switch (m_ptr->I_REQUEST) {   
   35     case GET_MACHINE: {
   36         length = sizeof(struct machine);
   37         src_phys = vir2phys(&machine);
   38         break;
   39     }
   40     case GET_KINFO: {
   41         length = sizeof(struct kinfo);
   42         src_phys = vir2phys(&kinfo);
   43         break;
   44     }
   45     case GET_IMAGE: {
   46         length = sizeof(struct boot_image) * NR_BOOT_PROCS;
   47         src_phys = vir2phys(image);
   48         break;
   49     }
   50     case GET_IRQHOOKS: {
   51         length = sizeof(struct irq_hook) * NR_IRQ_HOOKS;
   52         src_phys = vir2phys(irq_hooks);
   53         break;
   54     }
   55     case GET_SCHEDINFO: {
   56         /* This is slightly complicated because we need two data structures
   57          * at once, otherwise the scheduling information may be incorrect.
   58          * Copy the queue heads and fall through to copy the process table. 
   59          */
   60         length = sizeof(struct proc *) * NR_SCHED_QUEUES;
   61         src_phys = vir2phys(rdy_head);
   62         dst_phys = numap_local(m_ptr->m_source, (vir_bytes) m_ptr->I_VAL_PTR2,
   63                 length); 
   64         if (src_phys == 0 || dst_phys == 0) return(EFAULT);
   65         phys_copy(src_phys, dst_phys, length);
   66         /* fall through */
   67     }
   68     case GET_PROCTAB: {
   69         length = sizeof(struct proc) * (NR_PROCS + NR_TASKS);
   70         src_phys = vir2phys(proc);
   71         break;
   72     }
   73     case GET_PRIVTAB: {
   74         length = sizeof(struct priv) * (NR_SYS_PROCS);
   75         src_phys = vir2phys(priv);
   76         break;
   77     }
   78     case GET_PROC: {
   79         nr = (m_ptr->I_VAL_LEN2 == SELF) ? m_ptr->m_source : m_ptr->I_VAL_LEN2;
   80         if (! isokprocn(nr)) return(EINVAL);    /* validate request */
   81         length = sizeof(struct proc);
   82         src_phys = vir2phys(proc_addr(nr));
   83         break;
   84     }
   85     case GET_MONPARAMS: {
   86         src_phys = kinfo.params_base;           /* already is a physical */
   87         length = kinfo.params_size;
   88         break;
   89     }
   90     case GET_RANDOMNESS: {              
   91         static struct randomness copy;          /* copy to keep counters */
   92         int i;
   93 
   94         copy = krandom;
   95         for (i= 0; i<RANDOM_SOURCES; i++) {
   96                 krandom.bin[i].r_size = 0;      /* invalidate random data */
   97                 krandom.bin[i].r_next = 0;
   98         }
   99         length = sizeof(struct randomness);
  100         src_phys = vir2phys(&copy);
  101         break;
  102     }
  103     case GET_KMESSAGES: {
  104         length = sizeof(struct kmessages);
  105         src_phys = vir2phys(&kmess);
  106         break;
  107     }
  108 #if DEBUG_TIME_LOCKS
  109     case GET_LOCKTIMING: {
  110     length = sizeof(timingdata);
  111     src_phys = vir2phys(timingdata);
  112     break;
  113     }
  114 #endif
  115     case GET_BIOSBUFFER:
  116         bios_buf_vir = (vir_bytes)bios_buf;
  117         bios_buf_len = sizeof(bios_buf);
  118 
  119         length = sizeof(bios_buf_len);
  120         src_phys = vir2phys(&bios_buf_len);
  121         if (length != m_ptr->I_VAL_LEN2) return (EINVAL);
  122         proc_nr = m_ptr->m_source;      /* only caller can request copy */
  123         dst_phys = numap_local(proc_nr, (vir_bytes) m_ptr->I_VAL_PTR2, length); 
  124         if (src_phys == 0 || dst_phys == 0) return(EFAULT);
  125         phys_copy(src_phys, dst_phys, length);
  126 
  127         length = sizeof(bios_buf_vir);
  128         src_phys = vir2phys(&bios_buf_vir);
  129         break;
  130 
  131     default:
  132         return(EINVAL);
  133   }
  134 
  135   /* Try to make the actual copy for the requested data. */
  136   if (m_ptr->I_VAL_LEN > 0 && length > m_ptr->I_VAL_LEN) return (E2BIG);
  137   proc_nr = m_ptr->m_source;            /* only caller can request copy */
  138   dst_phys = numap_local(proc_nr, (vir_bytes) m_ptr->I_VAL_PTR, length); 
  139   if (src_phys == 0 || dst_phys == 0) return(EFAULT);
  140   phys_copy(src_phys, dst_phys, length);
  141   return(OK);
  142 }
  143 
  144 #endif /* USE_GETINFO */
  145 

Cache object: 7b3d83f78235abfdee9461faa98c3b48


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.