/* * cru_detect * * Routine Description: * This function uses the 32-bit BIOS Service Directory record to * search for a $CRU record. * * Return Value: * 0 : SUCCESS * <0 : FAILURE */ static int __devinit cru_detect(unsigned long map_entry, unsigned long map_offset) { void *bios32_map; unsigned long *bios32_entrypoint; unsigned long cru_physical_address; unsigned long cru_length; unsigned long physical_bios_base = 0; unsigned long physical_bios_offset = 0; int retval = -ENODEV; bios32_map = ioremap(map_entry, (2 * PAGE_SIZE)); if (bios32_map == NULL) return -ENODEV; bios32_entrypoint = bios32_map + map_offset; cmn_regs.u1.reax = CRU_BIOS_SIGNATURE_VALUE; set_memory_x((unsigned long)bios32_entrypoint, (2 * PAGE_SIZE)); asminline_call(&cmn_regs, bios32_entrypoint); if (cmn_regs.u1.ral != 0) { printk(KERN_WARNING "hpwdt: Call succeeded but with an error: 0x%x\n", cmn_regs.u1.ral); } else { physical_bios_base = cmn_regs.u2.rebx; physical_bios_offset = cmn_regs.u4.redx; cru_length = cmn_regs.u3.recx; cru_physical_address = physical_bios_base + physical_bios_offset; /* If the values look OK, then map it in. */ if ((physical_bios_base + physical_bios_offset)) { cru_rom_addr = ioremap(cru_physical_address, cru_length); if (cru_rom_addr) { set_memory_x((unsigned long)cru_rom_addr, cru_length); retval = 0; } } printk(KERN_DEBUG "hpwdt: CRU Base Address: 0x%lx\n", physical_bios_base); printk(KERN_DEBUG "hpwdt: CRU Offset Address: 0x%lx\n", physical_bios_offset); printk(KERN_DEBUG "hpwdt: CRU Length: 0x%lx\n", cru_length); printk(KERN_DEBUG "hpwdt: CRU Mapped Address: 0x%x\n", (unsigned int)&cru_rom_addr); } iounmap(bios32_map); return retval; }
static void __init early_mapping_set_exec(unsigned long start, unsigned long end, int executable) { unsigned long num_pages; start &= PMD_MASK; end = (end + PMD_SIZE - 1) & PMD_MASK; num_pages = (end - start) >> PAGE_SHIFT; if (executable) set_memory_x((unsigned long)__va(start), num_pages); else set_memory_nx((unsigned long)__va(start), num_pages); }
/* * cru_detect * * Routine Description: * This function uses the 32-bit BIOS Service Directory record to * search for a $CRU record. * * Return Value: * 0 : SUCCESS * <0 : FAILURE */ static int cru_detect(unsigned long map_entry, unsigned long map_offset) { void *bios32_map; unsigned long *bios32_entrypoint; unsigned long cru_physical_address; unsigned long cru_length; unsigned long physical_bios_base = 0; unsigned long physical_bios_offset = 0; int retval = -ENODEV; bios32_map = ioremap(map_entry, (2 * PAGE_SIZE)); if (bios32_map == NULL) return -ENODEV; bios32_entrypoint = bios32_map + map_offset; cmn_regs.u1.reax = CRU_BIOS_SIGNATURE_VALUE; set_memory_x((unsigned long)bios32_map, 2); asminline_call(&cmn_regs, bios32_entrypoint); if (cmn_regs.u1.ral != 0) { pr_warn("Call succeeded but with an error: 0x%x\n", cmn_regs.u1.ral); } else { physical_bios_base = cmn_regs.u2.rebx; physical_bios_offset = cmn_regs.u4.redx; cru_length = cmn_regs.u3.recx; cru_physical_address = physical_bios_base + physical_bios_offset; /* If the values look OK, then map it in. */ if ((physical_bios_base + physical_bios_offset)) { cru_rom_addr = ioremap(cru_physical_address, cru_length); if (cru_rom_addr) { set_memory_x((unsigned long)cru_rom_addr & PAGE_MASK, (cru_length + PAGE_SIZE - 1) >> PAGE_SHIFT); retval = 0; } } pr_debug("CRU Base Address: 0x%lx\n", physical_bios_base); pr_debug("CRU Offset Address: 0x%lx\n", physical_bios_offset); pr_debug("CRU Length: 0x%lx\n", cru_length); pr_debug("CRU Mapped Address: %p\n", &cru_rom_addr); }
/** * Initialize module. * * @returns appropriate status code. */ static int __init VBoxDrvLinuxInit(void) { int rc; /* * Check for synchronous/asynchronous TSC mode. */ printk(KERN_DEBUG "vboxdrv: Found %u processor cores\n", (unsigned)RTMpGetOnlineCount()); #ifdef CONFIG_VBOXDRV_AS_MISC rc = misc_register(&gMiscDeviceSys); if (rc) { printk(KERN_ERR "vboxdrv: Can't register system misc device! rc=%d\n", rc); return rc; } rc = misc_register(&gMiscDeviceUsr); if (rc) { printk(KERN_ERR "vboxdrv: Can't register user misc device! rc=%d\n", rc); misc_deregister(&gMiscDeviceSys); return rc; } #else /* !CONFIG_VBOXDRV_AS_MISC */ /* * Register character devices and save the returned major numbers. */ /* /dev/vboxdrv */ g_iModuleMajorSys = DEVICE_MAJOR_SYS; rc = register_chrdev((dev_t)g_iModuleMajorSys, DEVICE_NAME_SYS, &gFileOpsVBoxDrvSys); if (rc < 0) { Log(("register_chrdev() failed with rc=%#x for vboxdrv!\n", rc)); return rc; } if (DEVICE_MAJOR_SYS != 0) g_iModuleMajorSys = DEVICE_MAJOR_SYS; else g_iModuleMajorSys = rc; /* /dev/vboxdrvu */ /** @todo Use a minor number of this bugger (not sure if this code is used * though, so not bothering right now.) */ g_iModuleMajorUsr = DEVICE_MAJOR_USR; rc = register_chrdev((dev_t)g_iModuleMajorUsr, DEVICE_NAME_USR, &gFileOpsVBoxDrvUsr); if (rc < 0) { Log(("register_chrdev() failed with rc=%#x for vboxdrv!\n", rc)); return rc; } if (DEVICE_MAJOR_USR != 0) g_iModuleMajorUsr = DEVICE_MAJOR_USR; else g_iModuleMajorUsr = rc; rc = 0; # ifdef CONFIG_DEVFS_FS /* * Register a device entry */ if ( devfs_mk_cdev(MKDEV(DEVICE_MAJOR_SYS, 0), S_IFCHR | VBOX_DEV_FMASK, DEVICE_NAME_SYS) != 0 || devfs_mk_cdev(MKDEV(DEVICE_MAJOR_USR, 0), S_IFCHR | VBOX_DEV_FMASK, DEVICE_NAME_USR) != 0) { Log(("devfs_register failed!\n")); rc = -EINVAL; } # endif #endif /* !CONFIG_VBOXDRV_AS_MISC */ if (!rc) { /* * Initialize the runtime. * On AMD64 we'll have to donate the high rwx memory block to the exec allocator. */ rc = RTR0Init(0); if (RT_SUCCESS(rc)) { #if (defined(RT_ARCH_AMD64) && LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 23)) || defined(VBOX_WITH_TEXT_MODMEM_HACK) # ifdef VBOX_WITH_TEXT_MODMEM_HACK set_memory_x(&g_abExecMemory[0], sizeof(g_abExecMemory) / PAGE_SIZE); set_memory_rw(&g_abExecMemory[0], sizeof(g_abExecMemory) / PAGE_SIZE); # endif rc = RTR0MemExecDonate(&g_abExecMemory[0], sizeof(g_abExecMemory)); printk(KERN_DEBUG "VBoxDrv: dbg - g_abExecMemory=%p\n", (void *)&g_abExecMemory[0]); #endif Log(("VBoxDrv::ModuleInit\n")); /* * Initialize the device extension. */ if (RT_SUCCESS(rc)) rc = supdrvInitDevExt(&g_DevExt, sizeof(SUPDRVSESSION)); if (RT_SUCCESS(rc)) { #ifdef VBOX_WITH_SUSPEND_NOTIFICATION rc = platform_driver_register(&gPlatformDriver); if (rc == 0) { rc = platform_device_register(&gPlatformDevice); if (rc == 0) #endif { printk(KERN_INFO "vboxdrv: TSC mode is %s, tentative frequency %llu Hz\n", SUPGetGIPModeName(g_DevExt.pGip), g_DevExt.pGip->u64CpuHz); LogFlow(("VBoxDrv::ModuleInit returning %#x\n", rc)); printk(KERN_DEBUG "vboxdrv: Successfully loaded version " VBOX_VERSION_STRING " (interface " RT_XSTR(SUPDRV_IOC_VERSION) ")\n"); return rc; } #ifdef VBOX_WITH_SUSPEND_NOTIFICATION else platform_driver_unregister(&gPlatformDriver); } #endif } rc = -EINVAL; RTR0TermForced(); } else rc = -EINVAL; /* * Failed, cleanup and return the error code. */ #if defined(CONFIG_DEVFS_FS) && !defined(CONFIG_VBOXDRV_AS_MISC) devfs_remove(DEVICE_NAME_SYS); devfs_remove(DEVICE_NAME_USR); #endif } #ifdef CONFIG_VBOXDRV_AS_MISC misc_deregister(&gMiscDeviceSys); misc_deregister(&gMiscDeviceUsr); Log(("VBoxDrv::ModuleInit returning %#x (minor:%d & %d)\n", rc, gMiscDeviceSys.minor, gMiscDeviceUsr.minor)); #else unregister_chrdev(g_iModuleMajorUsr, DEVICE_NAME_USR); unregister_chrdev(g_iModuleMajorSys, DEVICE_NAME_SYS); Log(("VBoxDrv::ModuleInit returning %#x (major:%d & %d)\n", rc, g_iModuleMajorSys, g_iModuleMajorUsr)); #endif return rc; }