I\'ve ported my library x86Lib to mbed. It fully emulates the 8086 processor, but a few things I\'m still working on. Notable missing things are interrupts. Previously I used exceptions for interrupts, but exceptions aren\'t supported with the mbed compiler. It is also quite slow

Dependents:   x86Lib_Tester

Revision:
0:217a7931b41f
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/ops/store.cpp	Sun Mar 04 08:15:47 2012 +0000
@@ -0,0 +1,307 @@
+/**
+Copyright (c) 2007 - 2010 Jordan "Earlz/hckr83" Earls  <http://www.Earlz.biz.tm>
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+
+1. Redistributions of source code must retain the above copyright
+   notice, this list of conditions and the following disclaimer.
+2. Redistributions in binary form must reproduce the above copyright
+   notice, this list of conditions and the following disclaimer in the
+   documentation and/or other materials provided with the distribution.
+3. The name of the author may not be used to endorse or promote products
+   derived from this software without specific prior written permission.
+   
+THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
+INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL
+THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+This file is part of the x86Lib project.
+**/
+#define X86LIB_BUILD
+#include <x86Lib.h>
+namespace x86Lib{
+using namespace std;
+
+
+
+
+
+
+void x86CPU::op16_mov_r8_imm8(){ //0xB0+r
+    //I suppose the first real instruction is the hardest...
+    *regs8[op_cache[0]-0xB0]=op_cache[1];
+    eip++;
+}
+
+void x86CPU::op16_mov_r16_imm16(){ //0xB8+r
+    *regs16[op_cache[0]-0xB8]=*(uint16_t*)&op_cache[1];
+    eip+=2;
+}
+
+void x86CPU::op16_mov_sr_rm16(){ //0x8E
+    eip++;
+    ModRM16 rm16(this);
+    if(rm16.GetExtra()==cSS){ //if a mov into SS, then disable interrupts for 1 instruction.
+        cli_count=2;
+        freg._if=0;
+    }
+    seg[rm16.GetExtra()]=rm16.ReadWordr();
+}
+
+void x86CPU::op16_mov_rm16_sr(){ //0x8C
+    eip++;
+    ModRM16 rm16(this);
+    rm16.WriteWordr(seg[rm16.GetExtra()]);
+}
+
+
+
+void x86CPU::op16_mov_r16_rm16(){
+    eip++;
+    ModRM16 rm16(this);
+    *regs16[rm16.GetExtra()]=rm16.ReadWordr();
+}
+
+void x86CPU::op16_mov_rm16_r16(){
+    eip++;
+    ModRM16 rm16(this);
+    rm16.WriteWordr(*regs16[rm16.GetExtra()]);
+}
+
+void x86CPU::op16_mov_al_off8(){
+    *regs8[AL]=ReadByte(DS,*(uint16_t*)&op_cache[1]);
+    eip++;
+    eip++;
+}
+void x86CPU::op16_mov_ax_off16(){
+    *regs16[AX]=ReadWord(DS,*(uint16_t*)&op_cache[1]);
+    eip++;
+    eip++;
+}
+
+void x86CPU::op16_mov_rm8_r8(){
+    eip++;
+    ModRM16 rm(this);
+    rm.WriteByter(*regs8[rm.GetExtra()]);
+}
+
+void x86CPU::op16_mov_r8_rm8(){
+    eip++;
+    ModRM16 rm(this);
+    *regs8[rm.GetExtra()]=rm.ReadByter();
+}
+void x86CPU::op16_mov_off8_al(){
+    WriteByte(DS,*(uint16_t*)&op_cache[1],*regs8[AL]);
+    eip++;
+    eip++;
+}
+
+void x86CPU::op16_mov_off16_ax(){
+    WriteWord(DS,*(uint16_t*)&op_cache[1],*regs16[AX]);
+    eip++;eip++;
+}
+
+void x86CPU::op16_mov_m8_imm8(){
+    eip++;
+    ModRM16 rm(this);
+    
+    //eventually fix this so that if r is used, then invalid opcode...
+    rm.WriteByter(ReadByte(cCS,eip+rm.GetLength()));
+    eip++;
+}
+
+void x86CPU::op16_mov_m16_imm16(){
+    eip++;
+    ModRM16 rm(this);
+    rm.WriteWordr(ReadWord(cCS,eip+rm.GetLength()));
+    eip++;
+    eip++;
+}
+
+void x86CPU::op16_lds(){
+    eip++;
+    ModRM16 rm(this);
+    uint32_t tmp=rm.ReadDword();
+    seg[cDS]=(tmp&0xFFFF0000)>>16;
+    *regs16[rm.GetExtra()]=(tmp&0xFFFF);
+}
+
+void x86CPU::op16_les(){
+    eip++;
+    ModRM16 rm(this);
+    uint32_t tmp=rm.ReadDword();
+    seg[cES]=(tmp&0xFFFF0000)>>16;
+    *regs16[rm.GetExtra()]=(tmp&0xFFFF);
+}
+
+void x86CPU::op16_lea(){ //wtf is the point of this instruction! why not just mov reg,immediate! seriously frikkin crazy designers of x86
+    eip++;
+    ModRM16 rm(this);
+    *regs16[rm.GetExtra()]=rm.ReadOffset();
+}
+
+
+
+void x86CPU::op16_push_imm8(){
+    eip++;
+    Push16(op_cache[1]);
+}
+void x86CPU::op16_push_m16(ModRM16 &rm){
+    Push16(rm.ReadWordr());
+}
+
+void x86CPU::op16_push_imm16(){ //0x68
+    eip++;
+    Push16(*(uint16_t*)&op_cache[1]);
+    eip++;
+}
+
+
+void x86CPU::op16_push_r16(){ //0x50+reg
+    Push16(*regs16[op_cache[0]-0x50]);
+}
+
+void x86CPU::op16_push_es(){
+    Push16(seg[ES]);
+}
+
+void x86CPU::op16_push_cs(){
+    Push16(seg[CS]);
+}
+
+void x86CPU::op16_push_ds(){
+    Push16(seg[DS]);
+}
+
+
+void x86CPU::op16_push_ss(){
+    Push16(seg[SS]);
+}
+
+
+
+void x86CPU::op16_pop_m16(ModRM16 &rm){
+    rm.WriteWordr(Pop16());
+}
+
+void x86CPU::op16_pop_r16(){ //0x58+reg
+    *regs16[op_cache[0]-0x58]=Pop16();
+}
+
+
+void x86CPU::op16_pop_es(){
+    seg[ES]=Pop16();
+}
+
+void x86CPU::op16_pop_ss(){
+    cli_count=2;
+    freg._if=0;
+    seg[SS]=Pop16();
+}
+
+void x86CPU::op16_pop_ds(){
+    seg[DS]=Pop16();
+}
+
+
+
+void x86CPU::op16_out_imm8_al(){
+    Ports->Write(op_cache[1],1,(void*)regs8[AL]);
+    eip++;
+}
+
+void x86CPU::op16_out_imm8_ax(){
+    Ports->Write(op_cache[1],2,(void*)regs16[AX]);
+    eip++;
+}
+
+void x86CPU::op16_out_dx_al(){
+    Ports->Write(*regs16[DX],1,(void*)regs8[AL]);
+}
+
+void x86CPU::op16_out_dx_ax(){
+    Ports->Write(*regs16[DX],2,(void*)regs16[AX]);
+}
+
+
+void x86CPU::op16_in_al_imm8(){
+    Ports->Read(op_cache[1],1,(void*)regs8[AL]);
+    eip++;
+}
+
+void x86CPU::op16_in_ax_imm8(){
+    Ports->Read(op_cache[1],2,(void*)regs16[AX]);
+    eip++;
+}
+
+void x86CPU::op16_in_al_dx(){
+    Ports->Read(*regs16[DX],1,(void*)regs8[AL]);
+}
+
+void x86CPU::op16_in_ax_dx(){
+    Ports->Read(*regs16[DX],2,(void*)regs16[AX]);
+}
+
+
+
+void x86CPU::op16_xchg_rm8_r8(){
+    #ifndef X86_MULTITHREADING
+    if(IsLocked()==1){
+        eip--;
+        return;
+    }
+    #endif
+    Lock();
+    eip++;
+    ModRM16 rm(this);
+    uint8_t tmp=*regs8[rm.GetExtra()];
+    *regs8[rm.GetExtra()]=rm.ReadByter();
+    rm.WriteByter(tmp);
+    Unlock();
+}
+void x86CPU::op16_xchg_rm16_r16(){
+    #ifndef X86_MULTITHREADING
+    if(IsLocked()==1){
+        eip--;
+        return;
+    }
+    #endif
+    Lock();
+    eip++;
+    ModRM16 rm(this);
+    uint16_t tmp=*regs16[rm.GetExtra()];
+    *regs16[rm.GetExtra()]=rm.ReadWordr();
+    rm.WriteWordr(tmp);
+    Unlock();
+}
+
+void x86CPU::op16_xchg_ax_r16(){ //0x90+r
+    uint16_t tmp=*regs16[AX];
+    *regs16[AX]=*regs16[op_cache[0]-0x90];
+    *regs16[op_cache[0]-0x90]=tmp;
+}
+
+
+void x86CPU::op16_xlatb(){
+    *regs8[AL]=ReadByte(DS,(*regs16[BX])+(*regs8[AL]));
+}
+
+
+
+
+
+
+};
+
+
+