target-i386: move check_io helpers to seg_helper.c
Prepare for adding _kernel accessors there in the next patch. Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
This commit is contained in:
parent
43773ed369
commit
81cf8d8adc
|
@ -22,48 +22,6 @@
|
||||||
#include "exec/helper-proto.h"
|
#include "exec/helper-proto.h"
|
||||||
#include "exec/cpu_ldst.h"
|
#include "exec/cpu_ldst.h"
|
||||||
|
|
||||||
/* check if Port I/O is allowed in TSS */
|
|
||||||
static inline void check_io(CPUX86State *env, int addr, int size)
|
|
||||||
{
|
|
||||||
int io_offset, val, mask;
|
|
||||||
|
|
||||||
/* TSS must be a valid 32 bit one */
|
|
||||||
if (!(env->tr.flags & DESC_P_MASK) ||
|
|
||||||
((env->tr.flags >> DESC_TYPE_SHIFT) & 0xf) != 9 ||
|
|
||||||
env->tr.limit < 103) {
|
|
||||||
goto fail;
|
|
||||||
}
|
|
||||||
io_offset = cpu_lduw_kernel(env, env->tr.base + 0x66);
|
|
||||||
io_offset += (addr >> 3);
|
|
||||||
/* Note: the check needs two bytes */
|
|
||||||
if ((io_offset + 1) > env->tr.limit) {
|
|
||||||
goto fail;
|
|
||||||
}
|
|
||||||
val = cpu_lduw_kernel(env, env->tr.base + io_offset);
|
|
||||||
val >>= (addr & 7);
|
|
||||||
mask = (1 << size) - 1;
|
|
||||||
/* all bits must be zero to allow the I/O */
|
|
||||||
if ((val & mask) != 0) {
|
|
||||||
fail:
|
|
||||||
raise_exception_err(env, EXCP0D_GPF, 0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void helper_check_iob(CPUX86State *env, uint32_t t0)
|
|
||||||
{
|
|
||||||
check_io(env, t0, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
void helper_check_iow(CPUX86State *env, uint32_t t0)
|
|
||||||
{
|
|
||||||
check_io(env, t0, 2);
|
|
||||||
}
|
|
||||||
|
|
||||||
void helper_check_iol(CPUX86State *env, uint32_t t0)
|
|
||||||
{
|
|
||||||
check_io(env, t0, 4);
|
|
||||||
}
|
|
||||||
|
|
||||||
void helper_outb(uint32_t port, uint32_t data)
|
void helper_outb(uint32_t port, uint32_t data)
|
||||||
{
|
{
|
||||||
cpu_outb(port, data & 0xff);
|
cpu_outb(port, data & 0xff);
|
||||||
|
|
|
@ -2469,3 +2469,45 @@ void cpu_x86_load_seg(CPUX86State *env, int seg_reg, int selector)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* check if Port I/O is allowed in TSS */
|
||||||
|
static inline void check_io(CPUX86State *env, int addr, int size)
|
||||||
|
{
|
||||||
|
int io_offset, val, mask;
|
||||||
|
|
||||||
|
/* TSS must be a valid 32 bit one */
|
||||||
|
if (!(env->tr.flags & DESC_P_MASK) ||
|
||||||
|
((env->tr.flags >> DESC_TYPE_SHIFT) & 0xf) != 9 ||
|
||||||
|
env->tr.limit < 103) {
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
io_offset = cpu_lduw_kernel(env, env->tr.base + 0x66);
|
||||||
|
io_offset += (addr >> 3);
|
||||||
|
/* Note: the check needs two bytes */
|
||||||
|
if ((io_offset + 1) > env->tr.limit) {
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
val = cpu_lduw_kernel(env, env->tr.base + io_offset);
|
||||||
|
val >>= (addr & 7);
|
||||||
|
mask = (1 << size) - 1;
|
||||||
|
/* all bits must be zero to allow the I/O */
|
||||||
|
if ((val & mask) != 0) {
|
||||||
|
fail:
|
||||||
|
raise_exception_err(env, EXCP0D_GPF, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void helper_check_iob(CPUX86State *env, uint32_t t0)
|
||||||
|
{
|
||||||
|
check_io(env, t0, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void helper_check_iow(CPUX86State *env, uint32_t t0)
|
||||||
|
{
|
||||||
|
check_io(env, t0, 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
void helper_check_iol(CPUX86State *env, uint32_t t0)
|
||||||
|
{
|
||||||
|
check_io(env, t0, 4);
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in a new issue