mirror of
https://github.com/genodelabs/genode.git
synced 2024-12-20 14:13:09 +00:00
parent
824fb72694
commit
4c19576d4e
@ -1 +1 @@
|
|||||||
166105c79c2ebd0d8378af72bb4c392595c7bd67
|
59e99301300f881be06c12cd50fbe8b1164e1845
|
||||||
|
@ -21,7 +21,7 @@
|
|||||||
<ExtraDataItem name="GUI/LastNormalWindowPosition" value="513,100,1024,790"/>
|
<ExtraDataItem name="GUI/LastNormalWindowPosition" value="513,100,1024,790"/>
|
||||||
</ExtraData>
|
</ExtraData>
|
||||||
<Hardware version="2">
|
<Hardware version="2">
|
||||||
<CPU count="1" hotplug="false">
|
<CPU count="2" hotplug="false">
|
||||||
<HardwareVirtEx enabled="true"/>
|
<HardwareVirtEx enabled="true"/>
|
||||||
<HardwareVirtExNestedPaging enabled="true"/>
|
<HardwareVirtExNestedPaging enabled="true"/>
|
||||||
<HardwareVirtExVPID enabled="true"/>
|
<HardwareVirtExVPID enabled="true"/>
|
||||||
@ -46,7 +46,7 @@
|
|||||||
<RemoteDisplay enabled="false" authType="Null"/>
|
<RemoteDisplay enabled="false" authType="Null"/>
|
||||||
<BIOS>
|
<BIOS>
|
||||||
<ACPI enabled="true"/>
|
<ACPI enabled="true"/>
|
||||||
<IOAPIC enabled="false"/>
|
<IOAPIC enabled="true"/>
|
||||||
<Logo fadeIn="true" fadeOut="true" displayTime="0"/>
|
<Logo fadeIn="true" fadeOut="true" displayTime="0"/>
|
||||||
<BootMenu mode="MessageAndMenu"/>
|
<BootMenu mode="MessageAndMenu"/>
|
||||||
<TimeOffset value="0"/>
|
<TimeOffset value="0"/>
|
||||||
|
@ -21,7 +21,7 @@
|
|||||||
<ExtraDataItem name="GUI/LastNormalWindowPosition" value="0,12,1439,863"/>
|
<ExtraDataItem name="GUI/LastNormalWindowPosition" value="0,12,1439,863"/>
|
||||||
</ExtraData>
|
</ExtraData>
|
||||||
<Hardware version="2">
|
<Hardware version="2">
|
||||||
<CPU count="1" hotplug="false">
|
<CPU count="2" hotplug="false">
|
||||||
<HardwareVirtEx enabled="true"/>
|
<HardwareVirtEx enabled="true"/>
|
||||||
<HardwareVirtExNestedPaging enabled="true"/>
|
<HardwareVirtExNestedPaging enabled="true"/>
|
||||||
<HardwareVirtExVPID enabled="true"/>
|
<HardwareVirtExVPID enabled="true"/>
|
||||||
|
@ -84,7 +84,8 @@ bool create_emt_vcpu(pthread_t * thread, size_t stack_size,
|
|||||||
const pthread_attr_t *attr,
|
const pthread_attr_t *attr,
|
||||||
void *(*start_routine)(void *), void *arg,
|
void *(*start_routine)(void *), void *arg,
|
||||||
Genode::Cpu_session * cpu_session,
|
Genode::Cpu_session * cpu_session,
|
||||||
Genode::Affinity::Location location)
|
Genode::Affinity::Location location,
|
||||||
|
unsigned int cpu_id)
|
||||||
{
|
{
|
||||||
/* no hardware acceleration support */
|
/* no hardware acceleration support */
|
||||||
return false;
|
return false;
|
||||||
|
@ -38,14 +38,26 @@
|
|||||||
#include "vcpu_svm.h"
|
#include "vcpu_svm.h"
|
||||||
#include "vcpu_vmx.h"
|
#include "vcpu_vmx.h"
|
||||||
|
|
||||||
|
/* libc memory allocator */
|
||||||
static Vcpu_handler *vcpu_handler = 0;
|
#include <libc_mem_alloc.h>
|
||||||
|
|
||||||
|
|
||||||
static Genode::Semaphore *r0_halt_sem()
|
static Genode::List<Vcpu_handler> &vcpu_handler_list()
|
||||||
{
|
{
|
||||||
static Genode::Semaphore sem;
|
static Genode::List<Vcpu_handler> _inst;
|
||||||
return &sem;
|
return _inst;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static Vcpu_handler *lookup_vcpu_handler(unsigned int cpu_id)
|
||||||
|
{
|
||||||
|
for (Vcpu_handler *vcpu_handler = vcpu_handler_list().first();
|
||||||
|
vcpu_handler;
|
||||||
|
vcpu_handler = vcpu_handler->next())
|
||||||
|
if (vcpu_handler->cpu_id() == cpu_id)
|
||||||
|
return vcpu_handler;
|
||||||
|
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -80,7 +92,9 @@ int SUPR3CallVMMR0Fast(PVMR0 pVMR0, unsigned uOperation, VMCPUID idCpu)
|
|||||||
{
|
{
|
||||||
switch (uOperation) {
|
switch (uOperation) {
|
||||||
case SUP_VMMR0_DO_HM_RUN:
|
case SUP_VMMR0_DO_HM_RUN:
|
||||||
return vcpu_handler->run_hw(pVMR0, idCpu);
|
Vcpu_handler *vcpu_handler = lookup_vcpu_handler(idCpu);
|
||||||
|
Assert(vcpu_handler);
|
||||||
|
return vcpu_handler->run_hw(pVMR0);
|
||||||
}
|
}
|
||||||
return VERR_INTERNAL_ERROR;
|
return VERR_INTERNAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -95,13 +109,25 @@ int SUPR3CallVMMR0Ex(PVMR0 pVMR0, VMCPUID idCpu, unsigned
|
|||||||
genode_VMMR0_DO_GVMM_CREATE_VM(pReqHdr);
|
genode_VMMR0_DO_GVMM_CREATE_VM(pReqHdr);
|
||||||
return VINF_SUCCESS;
|
return VINF_SUCCESS;
|
||||||
|
|
||||||
case VMMR0_DO_GVMM_SCHED_HALT:
|
case VMMR0_DO_GVMM_REGISTER_VMCPU:
|
||||||
r0_halt_sem()->down();
|
genode_VMMR0_DO_GVMM_REGISTER_VMCPU(pVMR0, idCpu);
|
||||||
return VINF_SUCCESS;
|
return VINF_SUCCESS;
|
||||||
|
|
||||||
case VMMR0_DO_GVMM_SCHED_WAKE_UP:
|
case VMMR0_DO_GVMM_SCHED_HALT:
|
||||||
r0_halt_sem()->up();
|
{
|
||||||
|
Vcpu_handler *vcpu_handler = lookup_vcpu_handler(idCpu);
|
||||||
|
Assert(vcpu_handler);
|
||||||
|
vcpu_handler->halt();
|
||||||
return VINF_SUCCESS;
|
return VINF_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
case VMMR0_DO_GVMM_SCHED_WAKE_UP:
|
||||||
|
{
|
||||||
|
Vcpu_handler *vcpu_handler = lookup_vcpu_handler(idCpu);
|
||||||
|
Assert(vcpu_handler);
|
||||||
|
vcpu_handler->wake_up();
|
||||||
|
return VINF_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
/* called by 'vmR3HaltGlobal1Halt' */
|
/* called by 'vmR3HaltGlobal1Halt' */
|
||||||
case VMMR0_DO_GVMM_SCHED_POLL:
|
case VMMR0_DO_GVMM_SCHED_POLL:
|
||||||
@ -120,9 +146,13 @@ int SUPR3CallVMMR0Ex(PVMR0 pVMR0, VMCPUID idCpu, unsigned
|
|||||||
return VINF_SUCCESS;
|
return VINF_SUCCESS;
|
||||||
|
|
||||||
case VMMR0_DO_GVMM_SCHED_POKE:
|
case VMMR0_DO_GVMM_SCHED_POKE:
|
||||||
|
{
|
||||||
|
Vcpu_handler *vcpu_handler = lookup_vcpu_handler(idCpu);
|
||||||
|
Assert(vcpu_handler);
|
||||||
if (vcpu_handler)
|
if (vcpu_handler)
|
||||||
vcpu_handler->recall();
|
vcpu_handler->recall();
|
||||||
return VINF_SUCCESS;
|
return VINF_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
default:
|
default:
|
||||||
PERR("SUPR3CallVMMR0Ex: unhandled uOperation %d", uOperation);
|
PERR("SUPR3CallVMMR0Ex: unhandled uOperation %d", uOperation);
|
||||||
@ -213,23 +243,30 @@ bool create_emt_vcpu(pthread_t * pthread, size_t stack,
|
|||||||
const pthread_attr_t *attr,
|
const pthread_attr_t *attr,
|
||||||
void *(*start_routine)(void *), void *arg,
|
void *(*start_routine)(void *), void *arg,
|
||||||
Genode::Cpu_session * cpu_session,
|
Genode::Cpu_session * cpu_session,
|
||||||
Genode::Affinity::Location location)
|
Genode::Affinity::Location location,
|
||||||
|
unsigned int cpu_id)
|
||||||
{
|
{
|
||||||
Nova::Hip * hip = hip_rom.local_addr<Nova::Hip>();
|
Nova::Hip * hip = hip_rom.local_addr<Nova::Hip>();
|
||||||
|
|
||||||
if (!hip->has_feature_vmx() && !hip->has_feature_svm())
|
if (!hip->has_feature_vmx() && !hip->has_feature_svm())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
Vcpu_handler *vcpu_handler = 0;
|
||||||
|
|
||||||
if (hip->has_feature_vmx())
|
if (hip->has_feature_vmx())
|
||||||
vcpu_handler = new (0x10) Vcpu_handler_vmx(stack, attr, start_routine,
|
vcpu_handler = new (0x10) Vcpu_handler_vmx(stack, attr, start_routine,
|
||||||
arg, cpu_session, location);
|
arg, cpu_session, location,
|
||||||
|
cpu_id);
|
||||||
|
|
||||||
if (hip->has_feature_svm())
|
if (hip->has_feature_svm())
|
||||||
vcpu_handler = new (0x10) Vcpu_handler_svm(stack, attr, start_routine,
|
vcpu_handler = new (0x10) Vcpu_handler_svm(stack, attr, start_routine,
|
||||||
arg, cpu_session, location);
|
arg, cpu_session, location,
|
||||||
|
cpu_id);
|
||||||
|
|
||||||
Assert(!(reinterpret_cast<unsigned long>(vcpu_handler) & 0xf));
|
Assert(!(reinterpret_cast<unsigned long>(vcpu_handler) & 0xf));
|
||||||
|
|
||||||
|
vcpu_handler_list().insert(vcpu_handler);
|
||||||
|
|
||||||
*pthread = vcpu_handler;
|
*pthread = vcpu_handler;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -74,7 +74,8 @@ extern "C" int MMIO2_MAPPED_SYNC(PVM pVM, RTGCPHYS GCPhys, size_t cbWrite,
|
|||||||
bool &writeable);
|
bool &writeable);
|
||||||
|
|
||||||
|
|
||||||
class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>
|
class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>,
|
||||||
|
public Genode::List<Vcpu_handler>::Element
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
|
|
||||||
@ -87,6 +88,9 @@ class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>
|
|||||||
Genode::addr_t _ec_sel;
|
Genode::addr_t _ec_sel;
|
||||||
bool _irq_win;
|
bool _irq_win;
|
||||||
|
|
||||||
|
unsigned int _cpu_id;
|
||||||
|
Genode::Semaphore _halt_sem;
|
||||||
|
|
||||||
void fpu_save(char * data) {
|
void fpu_save(char * data) {
|
||||||
Assert(!(reinterpret_cast<Genode::addr_t>(data) & 0xF));
|
Assert(!(reinterpret_cast<Genode::addr_t>(data) & 0xF));
|
||||||
asm volatile ("fxsave %0" : "=m" (*data));
|
asm volatile ("fxsave %0" : "=m" (*data));
|
||||||
@ -219,7 +223,6 @@ class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>
|
|||||||
using namespace Genode;
|
using namespace Genode;
|
||||||
|
|
||||||
Assert(utcb->actv_state == ACTIVITY_STATE_ACTIVE);
|
Assert(utcb->actv_state == ACTIVITY_STATE_ACTIVE);
|
||||||
Assert(utcb->intr_state == INTERRUPT_STATE_NONE);
|
|
||||||
|
|
||||||
if (utcb->inj_info & IRQ_INJ_VALID_MASK)
|
if (utcb->inj_info & IRQ_INJ_VALID_MASK)
|
||||||
Vmm::printf("inj_info %x\n", utcb->inj_info);
|
Vmm::printf("inj_info %x\n", utcb->inj_info);
|
||||||
@ -635,16 +638,20 @@ class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>
|
|||||||
Vcpu_handler(size_t stack_size, const pthread_attr_t *attr,
|
Vcpu_handler(size_t stack_size, const pthread_attr_t *attr,
|
||||||
void *(*start_routine) (void *), void *arg,
|
void *(*start_routine) (void *), void *arg,
|
||||||
Genode::Cpu_session * cpu_session,
|
Genode::Cpu_session * cpu_session,
|
||||||
Genode::Affinity::Location location)
|
Genode::Affinity::Location location,
|
||||||
|
unsigned int cpu_id)
|
||||||
:
|
:
|
||||||
Vmm::Vcpu_dispatcher<pthread>(stack_size, _cap_connection,
|
Vmm::Vcpu_dispatcher<pthread>(stack_size, _cap_connection,
|
||||||
cpu_session, location,
|
cpu_session, location,
|
||||||
attr ? *attr : 0, start_routine, arg),
|
attr ? *attr : 0, start_routine, arg),
|
||||||
_vcpu(cpu_session, location),
|
_vcpu(cpu_session, location),
|
||||||
_ec_sel(Genode::cap_map()->insert()),
|
_ec_sel(Genode::cap_map()->insert()),
|
||||||
_irq_win(false)
|
_irq_win(false),
|
||||||
|
_cpu_id(cpu_id)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
|
unsigned int cpu_id() { return _cpu_id; }
|
||||||
|
|
||||||
void start() {
|
void start() {
|
||||||
_vcpu.start(_ec_sel);
|
_vcpu.start(_ec_sel);
|
||||||
}
|
}
|
||||||
@ -660,6 +667,16 @@ class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void halt()
|
||||||
|
{
|
||||||
|
_halt_sem.down();
|
||||||
|
}
|
||||||
|
|
||||||
|
void wake_up()
|
||||||
|
{
|
||||||
|
_halt_sem.up();
|
||||||
|
}
|
||||||
|
|
||||||
inline void dump_register_state(PCPUMCTX pCtx)
|
inline void dump_register_state(PCPUMCTX pCtx)
|
||||||
{
|
{
|
||||||
PINF("pCtx");
|
PINF("pCtx");
|
||||||
@ -742,10 +759,10 @@ class Vcpu_handler : public Vmm::Vcpu_dispatcher<pthread>
|
|||||||
PLOG("%x %x %x", utcb->intr_state, utcb->actv_state, utcb->mtd);
|
PLOG("%x %x %x", utcb->intr_state, utcb->actv_state, utcb->mtd);
|
||||||
}
|
}
|
||||||
|
|
||||||
int run_hw(PVMR0 pVMR0, VMCPUID idCpu)
|
int run_hw(PVMR0 pVMR0)
|
||||||
{
|
{
|
||||||
VM * pVM = reinterpret_cast<VM *>(pVMR0);
|
VM * pVM = reinterpret_cast<VM *>(pVMR0);
|
||||||
PVMCPU pVCpu = &pVM->aCpus[idCpu];
|
PVMCPU pVCpu = &pVM->aCpus[_cpu_id];
|
||||||
PCPUMCTX pCtx = CPUMQueryGuestCtxPtr(pVCpu);
|
PCPUMCTX pCtx = CPUMQueryGuestCtxPtr(pVCpu);
|
||||||
|
|
||||||
Nova::Utcb *utcb = reinterpret_cast<Nova::Utcb *>(Thread_base::utcb());
|
Nova::Utcb *utcb = reinterpret_cast<Nova::Utcb *>(Thread_base::utcb());
|
||||||
|
@ -84,10 +84,11 @@ class Vcpu_handler_svm : public Vcpu_handler
|
|||||||
Vcpu_handler_svm(size_t stack_size, const pthread_attr_t *attr,
|
Vcpu_handler_svm(size_t stack_size, const pthread_attr_t *attr,
|
||||||
void *(*start_routine) (void *), void *arg,
|
void *(*start_routine) (void *), void *arg,
|
||||||
Genode::Cpu_session * cpu_session,
|
Genode::Cpu_session * cpu_session,
|
||||||
Genode::Affinity::Location location)
|
Genode::Affinity::Location location,
|
||||||
|
unsigned int cpu_id)
|
||||||
:
|
:
|
||||||
Vcpu_handler(stack_size, attr, start_routine, arg, cpu_session,
|
Vcpu_handler(stack_size, attr, start_routine, arg, cpu_session,
|
||||||
location)
|
location, cpu_id)
|
||||||
{
|
{
|
||||||
using namespace Nova;
|
using namespace Nova;
|
||||||
|
|
||||||
|
@ -149,10 +149,11 @@ class Vcpu_handler_vmx : public Vcpu_handler
|
|||||||
Vcpu_handler_vmx(size_t stack_size, const pthread_attr_t *attr,
|
Vcpu_handler_vmx(size_t stack_size, const pthread_attr_t *attr,
|
||||||
void *(*start_routine) (void *), void *arg,
|
void *(*start_routine) (void *), void *arg,
|
||||||
Genode::Cpu_session * cpu_session,
|
Genode::Cpu_session * cpu_session,
|
||||||
Genode::Affinity::Location location)
|
Genode::Affinity::Location location,
|
||||||
|
unsigned int cpu_id)
|
||||||
:
|
:
|
||||||
Vcpu_handler(stack_size, attr, start_routine, arg, cpu_session,
|
Vcpu_handler(stack_size, attr, start_routine, arg, cpu_session,
|
||||||
location)
|
location, cpu_id)
|
||||||
{
|
{
|
||||||
using namespace Nova;
|
using namespace Nova;
|
||||||
|
|
||||||
|
@ -19,3 +19,4 @@ avoid_yield.patch
|
|||||||
serial.patch
|
serial.patch
|
||||||
rem_irq.patch
|
rem_irq.patch
|
||||||
usb.patch
|
usb.patch
|
||||||
|
tm_smp.patch
|
||||||
|
27
repos/ports/src/virtualbox/patches/tm_smp.patch
Normal file
27
repos/ports/src/virtualbox/patches/tm_smp.patch
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
tm_smp.patch
|
||||||
|
|
||||||
|
diff --git a/src/app/virtualbox/src/VBox/VMM/VMMR3/TM.cpp b/src/app/virtualbox/src/VBox/VMM/VMMR3/TM.cpp
|
||||||
|
index a5dc16e..df851a1 100644
|
||||||
|
--- a/src/app/virtualbox/src/VBox/VMM/VMMR3/TM.cpp
|
||||||
|
+++ b/src/app/virtualbox/src/VBox/VMM/VMMR3/TM.cpp
|
||||||
|
@@ -1901,10 +1901,19 @@ static DECLCALLBACK(void) tmR3TimerCallback(PRTTIMER pTimer, void *pvUser, uint6
|
||||||
|
NOREF(pTimer);
|
||||||
|
|
||||||
|
AssertCompile(TMCLOCK_MAX == 4);
|
||||||
|
+
|
||||||
|
+ if (VMCPU_FF_IS_SET(pVCpuDst, VMCPU_FF_TIMER)) {
|
||||||
|
#ifdef DEBUG_Sander /* very annoying, keep it private. */
|
||||||
|
- if (VMCPU_FF_IS_SET(pVCpuDst, VMCPU_FF_TIMER))
|
||||||
|
Log(("tmR3TimerCallback: timer event still pending!!\n"));
|
||||||
|
#endif
|
||||||
|
+ /*
|
||||||
|
+ * The VMCPU_FF_TIMER flag could have been set by a non-destination
|
||||||
|
+ * EMT thread without waking the destination EMT thread.
|
||||||
|
+ */
|
||||||
|
+ VMR3NotifyCpuFFU(pVCpuDst->pUVCpu, VMNOTIFYFF_FLAGS_DONE_REM);
|
||||||
|
+ return;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
if ( !VMCPU_FF_IS_SET(pVCpuDst, VMCPU_FF_TIMER)
|
||||||
|
&& ( pVM->tm.s.paTimerQueuesR3[TMCLOCK_VIRTUAL_SYNC].offSchedule /** @todo FIXME - reconsider offSchedule as a reason for running the timer queues. */
|
||||||
|
|| pVM->tm.s.paTimerQueuesR3[TMCLOCK_VIRTUAL].offSchedule
|
@ -672,6 +672,31 @@ extern "C" int MMIO2_MAPPED_SYNC(PVM pVM, RTGCPHYS GCPhys, size_t cbWrite,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Resets a virtual CPU when unplugged.
|
||||||
|
*
|
||||||
|
* @param pVM Pointer to the VM.
|
||||||
|
* @param pVCpu Pointer to the VMCPU.
|
||||||
|
*/
|
||||||
|
VMMR3DECL(void) PGMR3ResetCpu(PVM pVM, PVMCPU pVCpu)
|
||||||
|
{
|
||||||
|
int rc = PGMR3ChangeMode(pVM, pVCpu, PGMMODE_REAL);
|
||||||
|
AssertRC(rc);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Re-init other members.
|
||||||
|
*/
|
||||||
|
pVCpu->pgm.s.fA20Enabled = true;
|
||||||
|
pVCpu->pgm.s.GCPhysA20Mask = ~((RTGCPHYS)!pVCpu->pgm.s.fA20Enabled << 20);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Clear the FFs PGM owns.
|
||||||
|
*/
|
||||||
|
VMCPU_FF_CLEAR(pVCpu, VMCPU_FF_PGM_SYNC_CR3);
|
||||||
|
VMCPU_FF_CLEAR(pVCpu, VMCPU_FF_PGM_SYNC_CR3_NON_GLOBAL);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void PGMR3Reset(PVM pVM)
|
void PGMR3Reset(PVM pVM)
|
||||||
{
|
{
|
||||||
VM_ASSERT_EMT(pVM);
|
VM_ASSERT_EMT(pVM);
|
||||||
|
@ -26,6 +26,9 @@
|
|||||||
#include <iprt/uint128.h>
|
#include <iprt/uint128.h>
|
||||||
#include <VBox/err.h>
|
#include <VBox/err.h>
|
||||||
|
|
||||||
|
/* libc memory allocator */
|
||||||
|
#include <libc_mem_alloc.h>
|
||||||
|
|
||||||
|
|
||||||
struct Attached_gip : Genode::Attached_ram_dataspace
|
struct Attached_gip : Genode::Attached_ram_dataspace
|
||||||
{
|
{
|
||||||
@ -271,3 +274,58 @@ int SUPR3CallVMMR0(PVMR0 pVMR0, VMCPUID idCpu, unsigned uOperation,
|
|||||||
("SUPR3CallVMMR0Ex: unhandled uOperation %d", uOperation));
|
("SUPR3CallVMMR0Ex: unhandled uOperation %d", uOperation));
|
||||||
return VERR_GENERAL_FAILURE;
|
return VERR_GENERAL_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void genode_VMMR0_DO_GVMM_CREATE_VM(PSUPVMMR0REQHDR pReqHdr)
|
||||||
|
{
|
||||||
|
GVMMCREATEVMREQ &req = reinterpret_cast<GVMMCREATEVMREQ &>(*pReqHdr);
|
||||||
|
|
||||||
|
size_t const cCpus = req.cCpus;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Allocate and initialize VM struct
|
||||||
|
*
|
||||||
|
* The VM struct is followed by the variable-sizedA array of VMCPU
|
||||||
|
* objects. 'RT_UOFFSETOF' is used to determine the size including
|
||||||
|
* the VMCPU array.
|
||||||
|
*
|
||||||
|
* VM struct must be page-aligned, which is checked at least in
|
||||||
|
* PDMR3CritSectGetNop().
|
||||||
|
*/
|
||||||
|
size_t const cbVM = RT_UOFFSETOF(VM, aCpus[cCpus]);
|
||||||
|
VM *pVM = (VM *)Libc::mem_alloc()->alloc(cbVM, Genode::log2(PAGE_SIZE));
|
||||||
|
Genode::memset(pVM, 0, cbVM);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* On Genode, VMMR0 and VMMR3 share a single address space. Hence, the
|
||||||
|
* same pVM pointer is valid as pVMR0 and pVMR3.
|
||||||
|
*/
|
||||||
|
pVM->enmVMState = VMSTATE_CREATING;
|
||||||
|
pVM->pVMR0 = (RTHCUINTPTR)pVM;
|
||||||
|
pVM->pVMRC = (RTGCUINTPTR)pVM;
|
||||||
|
pVM->pSession = req.pSession;
|
||||||
|
pVM->cbSelf = cbVM;
|
||||||
|
pVM->cCpus = cCpus;
|
||||||
|
pVM->uCpuExecutionCap = 100; /* expected by 'vmR3CreateU()' */
|
||||||
|
pVM->offVMCPU = RT_UOFFSETOF(VM, aCpus);
|
||||||
|
|
||||||
|
for (uint32_t i = 0; i < cCpus; i++) {
|
||||||
|
pVM->aCpus[i].pVMR0 = pVM->pVMR0;
|
||||||
|
pVM->aCpus[i].pVMR3 = pVM;
|
||||||
|
pVM->aCpus[i].idHostCpu = NIL_RTCPUID;
|
||||||
|
pVM->aCpus[i].hNativeThreadR0 = NIL_RTNATIVETHREAD;
|
||||||
|
}
|
||||||
|
|
||||||
|
pVM->aCpus[0].hNativeThreadR0 = RTThreadNativeSelf();
|
||||||
|
|
||||||
|
/* out parameters of the request */
|
||||||
|
req.pVMR0 = pVM->pVMR0;
|
||||||
|
req.pVMR3 = pVM;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void genode_VMMR0_DO_GVMM_REGISTER_VMCPU(PVMR0 pVMR0, VMCPUID idCpu)
|
||||||
|
{
|
||||||
|
PVM pVM = reinterpret_cast<PVM>(pVMR0);
|
||||||
|
pVM->aCpus[idCpu].hNativeThreadR0 = RTThreadNativeSelf();
|
||||||
|
}
|
||||||
|
@ -16,17 +16,12 @@
|
|||||||
|
|
||||||
/* Genode includes */
|
/* Genode includes */
|
||||||
#include <cpu_session/cpu_session.h>
|
#include <cpu_session/cpu_session.h>
|
||||||
#include "util/misc_math.h"
|
|
||||||
#include "util/string.h"
|
|
||||||
|
|
||||||
/* VirtualBox includes */
|
/* VirtualBox includes */
|
||||||
#include <VBox/vmm/vm.h>
|
#include <VBox/vmm/vm.h>
|
||||||
#include <VBox/vmm/gvmm.h>
|
#include <VBox/vmm/gvmm.h>
|
||||||
#include <iprt/param.h>
|
#include <iprt/param.h>
|
||||||
|
|
||||||
/* libc memory allocator */
|
|
||||||
#include <libc_mem_alloc.h>
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns true if a vCPU could be started. If false we run without
|
* Returns true if a vCPU could be started. If false we run without
|
||||||
* hardware acceleration support.
|
* hardware acceleration support.
|
||||||
@ -35,57 +30,15 @@ bool create_emt_vcpu(pthread_t * pthread, size_t stack,
|
|||||||
const pthread_attr_t *attr,
|
const pthread_attr_t *attr,
|
||||||
void *(*start_routine)(void *), void *arg,
|
void *(*start_routine)(void *), void *arg,
|
||||||
Genode::Cpu_session * cpu_session,
|
Genode::Cpu_session * cpu_session,
|
||||||
Genode::Affinity::Location location);
|
Genode::Affinity::Location location,
|
||||||
|
unsigned int cpu_id);
|
||||||
|
|
||||||
|
|
||||||
uint64_t genode_cpu_hz();
|
uint64_t genode_cpu_hz();
|
||||||
|
|
||||||
|
|
||||||
void inline genode_VMMR0_DO_GVMM_CREATE_VM(PSUPVMMR0REQHDR pReqHdr)
|
|
||||||
{
|
|
||||||
GVMMCREATEVMREQ &req = reinterpret_cast<GVMMCREATEVMREQ &>(*pReqHdr);
|
|
||||||
|
|
||||||
size_t const cCpus = req.cCpus;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate and initialize VM struct
|
|
||||||
*
|
|
||||||
* The VM struct is followed by the variable-sizedA array of VMCPU
|
|
||||||
* objects. 'RT_UOFFSETOF' is used to determine the size including
|
|
||||||
* the VMCPU array.
|
|
||||||
*
|
|
||||||
* VM struct must be page-aligned, which is checked at least in
|
|
||||||
* PDMR3CritSectGetNop().
|
|
||||||
*/
|
|
||||||
size_t const cbVM = RT_UOFFSETOF(VM, aCpus[cCpus]);
|
|
||||||
VM *pVM = (VM *)Libc::mem_alloc()->alloc(cbVM, Genode::log2(PAGE_SIZE));
|
|
||||||
Genode::memset(pVM, 0, cbVM);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* On Genode, VMMR0 and VMMR3 share a single address space. Hence, the
|
|
||||||
* same pVM pointer is valid as pVMR0 and pVMR3.
|
|
||||||
*/
|
|
||||||
pVM->enmVMState = VMSTATE_CREATING;
|
|
||||||
pVM->pVMR0 = (RTHCUINTPTR)pVM;
|
|
||||||
pVM->pVMRC = (RTGCUINTPTR)pVM;
|
|
||||||
pVM->pSession = req.pSession;
|
|
||||||
pVM->cbSelf = cbVM;
|
|
||||||
pVM->cCpus = cCpus;
|
|
||||||
pVM->uCpuExecutionCap = 100; /* expected by 'vmR3CreateU()' */
|
|
||||||
pVM->offVMCPU = RT_UOFFSETOF(VM, aCpus);
|
|
||||||
|
|
||||||
for (uint32_t i = 0; i < cCpus; i++) {
|
|
||||||
pVM->aCpus[i].pVMR0 = pVM->pVMR0;
|
|
||||||
pVM->aCpus[i].pVMR3 = pVM;
|
|
||||||
pVM->aCpus[i].idHostCpu = NIL_RTCPUID;
|
|
||||||
pVM->aCpus[i].hNativeThreadR0 = NIL_RTNATIVETHREAD;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* out parameters of the request */
|
|
||||||
req.pVMR0 = pVM->pVMR0;
|
|
||||||
req.pVMR3 = pVM;
|
|
||||||
}
|
|
||||||
|
|
||||||
Genode::Cpu_session * get_vcpu_cpu_session();
|
Genode::Cpu_session * get_vcpu_cpu_session();
|
||||||
|
|
||||||
|
void genode_VMMR0_DO_GVMM_CREATE_VM(PSUPVMMR0REQHDR pReqHdr);
|
||||||
|
void genode_VMMR0_DO_GVMM_REGISTER_VMCPU(PVMR0 pVMR0, VMCPUID idCpu);
|
||||||
|
|
||||||
#endif /* _SUP_H_ */
|
#endif /* _SUP_H_ */
|
||||||
|
@ -25,6 +25,8 @@
|
|||||||
/* libc */
|
/* libc */
|
||||||
#include <pthread.h>
|
#include <pthread.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
/* vbox */
|
/* vbox */
|
||||||
#include <internal/thread.h>
|
#include <internal/thread.h>
|
||||||
@ -51,7 +53,7 @@ static Genode::Cpu_connection * cpu_connection(RTTHREADTYPE type) {
|
|||||||
|
|
||||||
char * data = new (env()->heap()) char[16];
|
char * data = new (env()->heap()) char[16];
|
||||||
|
|
||||||
snprintf(data, 16, "vbox %u", type);
|
Genode::snprintf(data, 16, "vbox %u", type);
|
||||||
|
|
||||||
con[type - 1] = new (env()->heap()) Cpu_connection(data, prio);
|
con[type - 1] = new (env()->heap()) Cpu_connection(data, prio);
|
||||||
|
|
||||||
@ -77,14 +79,20 @@ static int create_thread(pthread_t *thread, const pthread_attr_t *attr,
|
|||||||
stack_size);
|
stack_size);
|
||||||
|
|
||||||
/* sanity check - emt and vcpu thread have to have same prio class */
|
/* sanity check - emt and vcpu thread have to have same prio class */
|
||||||
if (!Genode::strcmp(rtthread->szName, "EMT"))
|
if (strstr(rtthread->szName, "EMT") == rtthread->szName)
|
||||||
Assert(rtthread->enmType == RTTHREADTYPE_EMULATION);
|
Assert(rtthread->enmType == RTTHREADTYPE_EMULATION);
|
||||||
|
|
||||||
if (rtthread->enmType == RTTHREADTYPE_EMULATION) {
|
if (rtthread->enmType == RTTHREADTYPE_EMULATION) {
|
||||||
|
|
||||||
|
unsigned int cpu_id = 0;
|
||||||
|
sscanf(rtthread->szName, "EMT-%u", &cpu_id);
|
||||||
|
|
||||||
Genode::Cpu_session * cpu_session = cpu_connection(RTTHREADTYPE_EMULATION);
|
Genode::Cpu_session * cpu_session = cpu_connection(RTTHREADTYPE_EMULATION);
|
||||||
Genode::Affinity::Location location;
|
Genode::Affinity::Space space = cpu_session->affinity_space();
|
||||||
|
Genode::Affinity::Location location(space.location_of_index(cpu_id));
|
||||||
|
|
||||||
if (create_emt_vcpu(thread, stack_size, attr, start_routine, arg,
|
if (create_emt_vcpu(thread, stack_size, attr, start_routine, arg,
|
||||||
cpu_session, location))
|
cpu_session, location, cpu_id))
|
||||||
return 0;
|
return 0;
|
||||||
/*
|
/*
|
||||||
* The virtualization layer had no need to setup the EMT
|
* The virtualization layer had no need to setup the EMT
|
||||||
|
@ -79,7 +79,6 @@ DUMMY(PGMR3LockCall)
|
|||||||
DUMMY(PGMR3PoolGrow)
|
DUMMY(PGMR3PoolGrow)
|
||||||
DUMMY(PGMR3QueryGlobalMemoryStats)
|
DUMMY(PGMR3QueryGlobalMemoryStats)
|
||||||
DUMMY(PGMR3QueryMemoryStats)
|
DUMMY(PGMR3QueryMemoryStats)
|
||||||
DUMMY(PGMR3ResetCpu)
|
|
||||||
|
|
||||||
DUMMY(PGMR3PhysAllocateHandyPages)
|
DUMMY(PGMR3PhysAllocateHandyPages)
|
||||||
DUMMY(PGMR3PhysAllocateLargeHandyPage)
|
DUMMY(PGMR3PhysAllocateLargeHandyPage)
|
||||||
|
Loading…
Reference in New Issue
Block a user