X-Git-Url: http://v3vee.org/palacios/gitweb/gitweb.cgi?a=blobdiff_plain;f=palacios%2Finclude%2Fpalacios%2Fvmm_instr_emulator.h;h=132970b08668a08017789a24b4aa403850259bd5;hb=75aa9d6205930057dc8163238d325558bcb1fd9b;hp=190dcee93d2911b567ca08fc1f19d9674314a61f;hpb=da0f0deecf22754656bad2a95640461ec3ac4f1d;p=palacios.releases.git diff --git a/palacios/include/palacios/vmm_instr_emulator.h b/palacios/include/palacios/vmm_instr_emulator.h index 190dcee..132970b 100644 --- a/palacios/include/palacios/vmm_instr_emulator.h +++ b/palacios/include/palacios/vmm_instr_emulator.h @@ -1,8 +1,27 @@ +/* + * This file is part of the Palacios Virtual Machine Monitor developed + * by the V3VEE Project with funding from the United States National + * Science Foundation and the Department of Energy. + * + * The V3VEE Project is a joint project between Northwestern University + * and the University of New Mexico. You can find out more at + * http://www.v3vee.org + * + * Copyright (c) 2008, Jack Lange + * Copyright (c) 2008, The V3VEE Project + * All rights reserved. + * + * Author: Jack Lange + * + * This is free software. You are permitted to use, + * redistribute, and modify it as specified in the file "V3VEE_LICENSE". + */ + #include -#define MAKE_1OP_8FLAGS_INST(iname) static inline void iname##8(addr_t * dst, addr_t * flags) { \ +#define MAKE_1OP_8FLAGS_WINST(iname) static inline void iname##8(addr_t * dst, addr_t * flags) { \ uchar_t tmp_dst = *dst; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -24,7 +43,7 @@ \ } -#define MAKE_1OP_16FLAGS_INST(iname) static inline void iname##16(addr_t * dst, addr_t * flags) { \ +#define MAKE_1OP_16FLAGS_WINST(iname) static inline void iname##16(addr_t * dst, addr_t * flags) { \ ushort_t tmp_dst = *dst; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -46,7 +65,7 @@ \ } -#define MAKE_1OP_32FLAGS_INST(iname) static inline void iname##32(addr_t * dst, addr_t * flags) { \ +#define MAKE_1OP_32FLAGS_WINST(iname) static inline void iname##32(addr_t * dst, addr_t * flags) { \ uint_t tmp_dst = *dst; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -68,7 +87,7 @@ \ } -#define MAKE_1OP_64FLAGS_INST(iname) static inline void iname##64(addr_t * dst, addr_t * flags) { \ +#define MAKE_1OP_64FLAGS_WINST(iname) static inline void iname##64(addr_t * dst, addr_t * flags) { \ ullong_t tmp_dst = *dst; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -92,7 +111,7 @@ -#define MAKE_1OP_8_INST(iname) static inline void iname##8(addr_t * dst) { \ +#define MAKE_1OP_8_WINST(iname) static inline void iname##8(addr_t * dst) { \ uchar_t tmp_dst = *dst; \ \ asm volatile ( \ @@ -103,7 +122,7 @@ *dst = tmp_dst; \ } -#define MAKE_1OP_16_INST(iname) static inline void iname##16(addr_t * dst) { \ +#define MAKE_1OP_16_WINST(iname) static inline void iname##16(addr_t * dst) { \ ushort_t tmp_dst = *dst; \ \ asm volatile ( \ @@ -114,7 +133,7 @@ *dst = tmp_dst; \ } -#define MAKE_1OP_32_INST(iname) static inline void iname##32(addr_t * dst) { \ +#define MAKE_1OP_32_WINST(iname) static inline void iname##32(addr_t * dst) { \ uint_t tmp_dst = *dst; \ \ asm volatile ( \ @@ -125,7 +144,7 @@ *dst = tmp_dst; \ } -#define MAKE_1OP_64_INST(iname) static inline void iname##64(addr_t * dst) { \ +#define MAKE_1OP_64_WINST(iname) static inline void iname##64(addr_t * dst) { \ ullong_t tmp_dst = *dst; \ \ asm volatile ( \ @@ -137,7 +156,7 @@ } -#define MAKE_2OP_64FLAGS_INST(iname) static inline void iname##64(addr_t * dst, addr_t * src, addr_t * flags) { \ +#define MAKE_2OP_64FLAGS_WINST(iname) static inline void iname##64(addr_t * dst, addr_t * src, addr_t * flags) { \ uint64_t tmp_dst = *dst, tmp_src = *src; \ addr_t tmp_flags = *flags; \ \ @@ -165,7 +184,7 @@ -#define MAKE_2OP_32FLAGS_INST(iname) static inline void iname##32(addr_t * dst, addr_t * src, addr_t * flags) { \ +#define MAKE_2OP_32FLAGS_WINST(iname) static inline void iname##32(addr_t * dst, addr_t * src, addr_t * flags) { \ uint32_t tmp_dst = *dst, tmp_src = *src; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -188,7 +207,7 @@ } -#define MAKE_2OP_16FLAGS_INST(iname) static inline void iname##16(addr_t * dst, addr_t * src, addr_t * flags) { \ +#define MAKE_2OP_16FLAGS_WINST(iname) static inline void iname##16(addr_t * dst, addr_t * src, addr_t * flags) { \ ushort_t tmp_dst = *dst, tmp_src = *src; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -210,7 +229,7 @@ \ } -#define MAKE_2OP_8FLAGS_INST(iname) static inline void iname##8(addr_t * dst, addr_t * src, addr_t * flags) { \ +#define MAKE_2OP_8FLAGS_WINST(iname) static inline void iname##8(addr_t * dst, addr_t * src, addr_t * flags) { \ uchar_t tmp_dst = *dst, tmp_src = *src; \ \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -235,7 +254,32 @@ -#define MAKE_2OP_32STR_INST(iname) static inline void iname##32(addr_t * dst, \ + +#define MAKE_2OP_64STR_WINST(iname) static inline void iname##64(addr_t * dst, \ + addr_t * src, \ + addr_t * ecx, addr_t * flags) { \ + /* Some of the flags values are not copied out in a pushf, we save them here */ \ + addr_t flags_rsvd = *flags & ~0xfffe7fff; \ + \ + asm volatile ( \ + "pushfq; " \ + "pushq %4; " \ + "popfq; " \ + "rep; " \ + #iname"q; " \ + "pushfq; " \ + "popq %0; " \ + "popfq; " \ + : "=q"(*flags) \ + : "D"(*dst),"S"(*src),"c"(*ecx),"q"(*flags) \ + ); \ + \ + /* : "=D"(*dst),"=S"(*src),"=c"(*ecx),"=q"(*flags)*/ \ + *flags |= flags_rsvd; \ + } + + +#define MAKE_2OP_32STR_WINST(iname) static inline void iname##32(addr_t * dst, \ addr_t * src, \ addr_t * ecx, addr_t * flags) { \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -250,15 +294,15 @@ "pushf; " \ "pop %0; " \ "popf; " \ - : "=b"(*flags) \ - : "D"(*dst),"S"(*src),"c"(*ecx),"b"(*flags) \ + : "=q"(*flags) \ + : "D"(*dst),"S"(*src),"c"(*ecx),"q"(*flags) \ ); \ \ /* : "=D"(*dst),"=S"(*src),"=c"(*ecx),"=q"(*flags)*/ \ *flags |= flags_rsvd; \ } -#define MAKE_2OP_16STR_INST(iname) static inline void iname##16(addr_t * dst, \ +#define MAKE_2OP_16STR_WINST(iname) static inline void iname##16(addr_t * dst, \ addr_t * src, \ addr_t * ecx, addr_t * flags) { \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -273,15 +317,15 @@ "pushf; " \ "pop %0; " \ "popf; " \ - : "=b"(*flags) \ - : "D"(*dst),"S"(*src),"c"(*ecx),"b"(*flags) \ + : "=q"(*flags) \ + : "D"(*dst),"S"(*src),"c"(*ecx),"q"(*flags) \ ); \ *flags |= flags_rsvd; \ } -#define MAKE_2OP_8STR_INST(iname) static inline void iname##8(addr_t * dst, \ +#define MAKE_2OP_8STR_WINST(iname) static inline void iname##8(addr_t * dst, \ addr_t * src, \ addr_t * ecx, addr_t * flags) { \ /* Some of the flags values are not copied out in a pushf, we save them here */ \ @@ -296,8 +340,8 @@ "pushf; " \ "pop %0; " \ "popf; " \ - : "=b"(*flags) \ - : "D"(*dst),"S"(*src),"c"(*ecx),"b"(*flags) \ + : "=q"(*flags) \ + : "D"(*dst),"S"(*src),"c"(*ecx),"q"(*flags) \ ); \ *flags |= flags_rsvd; \ } @@ -305,7 +349,18 @@ -#define MAKE_2OP_32_INST(iname) static inline void iname##32(addr_t * dst, addr_t * src) { \ +#define MAKE_2OP_64_WINST(iname) static inline void iname##64(addr_t * dst, addr_t * src) { \ + uint32_t tmp_dst = *dst, tmp_src = *src; \ + \ + asm volatile ( \ + #iname"q %1, %0; " \ + : "=q"(tmp_dst) \ + : "q"(tmp_src), "0"(tmp_dst) \ + ); \ + *dst = tmp_dst; \ + } + +#define MAKE_2OP_32_WINST(iname) static inline void iname##32(addr_t * dst, addr_t * src) { \ uint32_t tmp_dst = *dst, tmp_src = *src; \ \ asm volatile ( \ @@ -316,7 +371,7 @@ *dst = tmp_dst; \ } -#define MAKE_2OP_16_INST(iname) static inline void iname##16(addr_t * dst, addr_t * src) { \ +#define MAKE_2OP_16_WINST(iname) static inline void iname##16(addr_t * dst, addr_t * src) { \ ushort_t tmp_dst = *dst, tmp_src = *src; \ \ asm volatile ( \ @@ -327,7 +382,7 @@ *dst = tmp_dst; \ } -#define MAKE_2OP_8_INST(iname) static inline void iname##8(addr_t * dst, addr_t * src) { \ +#define MAKE_2OP_8_WINST(iname) static inline void iname##8(addr_t * dst, addr_t * src) { \ uchar_t tmp_dst = *dst, tmp_src = *src; \ \ asm volatile ( \ @@ -344,80 +399,80 @@ -MAKE_2OP_8FLAGS_INST(adc); -MAKE_2OP_8FLAGS_INST(add); -MAKE_2OP_8FLAGS_INST(and); -MAKE_2OP_8FLAGS_INST(or); -MAKE_2OP_8FLAGS_INST(xor); -MAKE_2OP_8FLAGS_INST(sub); +MAKE_2OP_8FLAGS_WINST(adc); +MAKE_2OP_8FLAGS_WINST(add); +MAKE_2OP_8FLAGS_WINST(and); +MAKE_2OP_8FLAGS_WINST(or); +MAKE_2OP_8FLAGS_WINST(xor); +MAKE_2OP_8FLAGS_WINST(sub); -MAKE_1OP_8FLAGS_INST(inc); -MAKE_1OP_8FLAGS_INST(dec); -MAKE_1OP_8FLAGS_INST(neg); -MAKE_1OP_8FLAGS_INST(setb); -MAKE_1OP_8FLAGS_INST(setbe); -MAKE_1OP_8FLAGS_INST(setl); -MAKE_1OP_8FLAGS_INST(setle); -MAKE_1OP_8FLAGS_INST(setnb); -MAKE_1OP_8FLAGS_INST(setnbe); -MAKE_1OP_8FLAGS_INST(setnl); -MAKE_1OP_8FLAGS_INST(setnle); -MAKE_1OP_8FLAGS_INST(setno); -MAKE_1OP_8FLAGS_INST(setnp); -MAKE_1OP_8FLAGS_INST(setns); -MAKE_1OP_8FLAGS_INST(setnz); -MAKE_1OP_8FLAGS_INST(seto); -MAKE_1OP_8FLAGS_INST(setp); -MAKE_1OP_8FLAGS_INST(sets); -MAKE_1OP_8FLAGS_INST(setz); +MAKE_1OP_8FLAGS_WINST(inc); +MAKE_1OP_8FLAGS_WINST(dec); +MAKE_1OP_8FLAGS_WINST(neg); +MAKE_1OP_8FLAGS_WINST(setb); +MAKE_1OP_8FLAGS_WINST(setbe); +MAKE_1OP_8FLAGS_WINST(setl); +MAKE_1OP_8FLAGS_WINST(setle); +MAKE_1OP_8FLAGS_WINST(setnb); +MAKE_1OP_8FLAGS_WINST(setnbe); +MAKE_1OP_8FLAGS_WINST(setnl); +MAKE_1OP_8FLAGS_WINST(setnle); +MAKE_1OP_8FLAGS_WINST(setno); +MAKE_1OP_8FLAGS_WINST(setnp); +MAKE_1OP_8FLAGS_WINST(setns); +MAKE_1OP_8FLAGS_WINST(setnz); +MAKE_1OP_8FLAGS_WINST(seto); +MAKE_1OP_8FLAGS_WINST(setp); +MAKE_1OP_8FLAGS_WINST(sets); +MAKE_1OP_8FLAGS_WINST(setz); -MAKE_1OP_8_INST(not); +MAKE_1OP_8_WINST(not); -MAKE_2OP_8_INST(mov); -MAKE_2OP_8_INST(xchg); +MAKE_2OP_8_WINST(mov); +MAKE_2OP_8_WINST(xchg); -MAKE_2OP_16FLAGS_INST(adc); -MAKE_2OP_16FLAGS_INST(add); -MAKE_2OP_16FLAGS_INST(and); -MAKE_2OP_16FLAGS_INST(or); -MAKE_2OP_16FLAGS_INST(xor); -MAKE_2OP_16FLAGS_INST(sub); +MAKE_2OP_16FLAGS_WINST(adc); +MAKE_2OP_16FLAGS_WINST(add); +MAKE_2OP_16FLAGS_WINST(and); +MAKE_2OP_16FLAGS_WINST(or); +MAKE_2OP_16FLAGS_WINST(xor); +MAKE_2OP_16FLAGS_WINST(sub); -MAKE_1OP_16FLAGS_INST(inc); -MAKE_1OP_16FLAGS_INST(dec); -MAKE_1OP_16FLAGS_INST(neg); +MAKE_1OP_16FLAGS_WINST(inc); +MAKE_1OP_16FLAGS_WINST(dec); +MAKE_1OP_16FLAGS_WINST(neg); -MAKE_1OP_16_INST(not); +MAKE_1OP_16_WINST(not); -MAKE_2OP_16_INST(mov); -MAKE_2OP_16_INST(xchg); +MAKE_2OP_16_WINST(mov); +MAKE_2OP_16_WINST(xchg); -MAKE_2OP_32FLAGS_INST(adc); -MAKE_2OP_32FLAGS_INST(add); -MAKE_2OP_32FLAGS_INST(and); -MAKE_2OP_32FLAGS_INST(or); -MAKE_2OP_32FLAGS_INST(xor); -MAKE_2OP_32FLAGS_INST(sub); +MAKE_2OP_32FLAGS_WINST(adc); +MAKE_2OP_32FLAGS_WINST(add); +MAKE_2OP_32FLAGS_WINST(and); +MAKE_2OP_32FLAGS_WINST(or); +MAKE_2OP_32FLAGS_WINST(xor); +MAKE_2OP_32FLAGS_WINST(sub); -MAKE_1OP_32FLAGS_INST(inc); -MAKE_1OP_32FLAGS_INST(dec); -MAKE_1OP_32FLAGS_INST(neg); +MAKE_1OP_32FLAGS_WINST(inc); +MAKE_1OP_32FLAGS_WINST(dec); +MAKE_1OP_32FLAGS_WINST(neg); -MAKE_1OP_32_INST(not); +MAKE_1OP_32_WINST(not); -MAKE_2OP_32_INST(mov); -MAKE_2OP_32_INST(xchg); +MAKE_2OP_32_WINST(mov); +MAKE_2OP_32_WINST(xchg); -MAKE_2OP_8STR_INST(movs); -MAKE_2OP_16STR_INST(movs); -MAKE_2OP_32STR_INST(movs); +MAKE_2OP_8STR_WINST(movs); +MAKE_2OP_16STR_WINST(movs); +MAKE_2OP_32STR_WINST(movs);