#include <kern/machine.h>
#include <kern/processor.h>
#include <mach/machine.h>
#include <mach/processor_info.h>
#include <mach/mach_types.h>
#include <mach/boolean.h>
#include <kern/thread.h>
#include <kern/task.h>
#include <kern/ipc_kobject.h>
#include <mach/vm_param.h>
#include <ipc/port.h>
#include <ipc/ipc_entry.h>
#include <ipc/ipc_space.h>
#include <ipc/ipc_object.h>
#include <ipc/ipc_port.h>
#include <vm/vm_kern.h>
#include <vm/vm_map.h>
#include <vm/vm_page.h>
#include <vm/pmap.h>
#include <pexpert/pexpert.h>
#include <console/video_console.h>
#include <i386/cpu_data.h>
#include <i386/Diagnostics.h>
#include <i386/mp.h>
#include <i386/pmCPU.h>
#include <i386/tsc.h>
#include <mach/i386/syscall_sw.h>
#include <kern/kalloc.h>
#include <sys/kdebug.h>
diagWork dgWork;
uint64_t lastRuptClear = 0ULL;
int
diagCall64(x86_saved_state_t * state)
{
uint64_t curpos, i, j;
uint64_t selector, data;
uint64_t currNap, durNap;
x86_saved_state64_t *regs;
boolean_t diagflag;
assert(is_saved_state64(state));
regs = saved_state64(state);
diagflag = ((dgWork.dgFlags & enaDiagSCs) != 0);
selector = regs->rdi;
switch (selector) {
case dgRuptStat:
(void) ml_set_interrupts_enabled(TRUE);
if (diagflag == 0)
break;
data = regs->rsi;
if (data == 0) {
for (i = 0; i < real_ncpus; i++) {
for (j = 0; j < 256; j++)
cpu_data_ptr[i]->cpu_hwIntCnt[j] = 0;
}
lastRuptClear = mach_absolute_time();
return 1;
}
(void) copyout((char *) &real_ncpus, data, sizeof(real_ncpus));
currNap = mach_absolute_time();
durNap = currNap - lastRuptClear;
if (durNap == 0)
durNap = 1;
curpos = data + sizeof(real_ncpus);
for (i = 0; i < real_ncpus; i++) {
(void) copyout((char *) &durNap, curpos, 8);
(void) copyout((char *) &cpu_data_ptr[i]->cpu_hwIntCnt, curpos + 8, 256 * sizeof(uint32_t));
curpos = curpos + (256 * sizeof(uint32_t) + 8);
}
return 1;
break;
#if DEBUG
case dgGzallocTest:
{
(void) ml_set_interrupts_enabled(TRUE);
if (diagflag == 0)
break;
unsigned *ptr = (unsigned *)kalloc(1024);
kfree(ptr, 1024);
*ptr = 0x42;
}
break;
#endif
#if defined(__x86_64__)
case dgPermCheck:
{
(void) ml_set_interrupts_enabled(TRUE);
if (diagflag == 0)
break;
return pmap_permissions_verify(kernel_pmap, kernel_map, 0, ~0ULL);
}
break;
#endif
default:
return 0;
}
return 1;
}