📄 star.c
字号:
emit("xor ch,cl\n"); emit("jz near ln%d\n", myline); /* If so, swap stack pointers */ emit("mov ecx,[__a7]\n"); emit("xchg ecx,[__asp]\n"); emit("mov [__a7],ecx\n"); /* and copy the appropriate memory map */ emit("test byte[esp+1],20h\n"); emit("jz short ln%d\n", myline + 1); copy_memory_map("s", "ecx"); emit("jmp short ln%d\n", myline); emit("ln%d:\n", myline + 1); copy_memory_map("u", "ecx"); emit("ln%d:\n", myline); emit("pop ecx\n"); /* Step 2: set new PPL / supervisor mode / trace flag */ emit("mov [__sr+1],ch\n"); emit("and byte[__sr+1],0A7h\n"); /* Step 3: Store CL into CCR */ cl2ccr();}/* Read flags from our CCR into CL. CH is zeroed. */static void ccr2cl(void){ /* Read XNZ */ emit("mov ch,[__xflag]\n"); /* 0000000X???????? */ emit("mov cl,ah\n"); /* 0000000XNZ?????C */ emit("shr cx,6\n"); /* 0000000000000XNZ */ /* Read V */ emit("add cl,cl\n"); /* 000000000000XNZ0 */ emit("or cl,al\n"); /* 000000000000XNZV */ /* Read C */ emit("mov ch,ah\n"); /* NZ?????C0000XNZV */ emit("shl ch,8\n"); /* 000000000000XNZV carry */ emit("adc cl,cl\n"); /* 00000000000XNZVC */}/* Read flags from our SR into CX. */static void sr2cx(void){ /* Condition codes */ ccr2cl(); /* PPL / supervisor mode / trace flag */ emit("mov ch,[__sr+1]\n");}/* Switch to supervisor mode. Can potentially destroy ECX. */static void supervisor(void){ int myline=linenum;linenum++; emit("test byte[__sr+1],20h\n"); emit("jnz short ln%d\n",myline); emit("mov ecx,[__a7]\n"); emit("xchg ecx,[__asp]\n"); emit("mov [__a7],ecx\n"); copy_memory_map("s", "ecx"); emit("or byte[__sr+1],20h\n"); emit("ln%d:\n",myline);}/***************************************************************************/static void gen_readbw(int size){ char z='x'; if(size==1)z='b'; if(size==2)z='w'; align(16); emit("readmemory%s:\n",sizename[size]); emit("mov [__access_address],edx\n"); maskaddress("edx"); emit("mov ecx,[__read%s]\n",sizename[size]); emit("read%c_check:\n",z); emit("cmp edx,[ecx]\n"); /* Are we smaller? */ emit("jb short read%c_next\n",z); /* Yes, go to next address */ emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */ emit("jbe short read%c_call\n",z); emit("read%c_next:\n",z); emit("cmp dword[ecx],byte -1\n");/* End of list? */ emit("je short read%c_outofrange\n",z); emit("add ecx,byte 16\n"); /* To the next structure */ emit("jmp short read%c_check\n",z); emit("read%c_outofrange:\n",z); emit("or ecx,byte -1\n"); emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("read%c_call:\n",z); emit("cmp dword[ecx+8],byte 0\n"); emit("jne short read%c_callio\n",z);#ifndef RAINE emit("sub edx,[ecx]\n");#endif emit("add edx,[ecx+12]\n"); if(size==1){ emit("xor edx,byte 1\n"); emit("mov cl,[edx]\n"); }else{ emit("mov cx,[edx]\n"); } emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("read%c_callio:\n",z); airlock_exit(); /* ** What's this undocumented thingy? Read/write handlers actually get ** an extra parameter (the address of the record that caused the ** call). */ emit("mov eax,edx\n"); /* address */ emit("mov edx,ecx\n"); /* pointer to structure */ if(use_stack){ emit("push edx\n"); emit("push eax\n"); } emit("call dword[edx+8]\n"); if(use_stack)emit("add esp,byte 8\n"); emit("mov ecx,eax\n"); airlock_enter(); emit("mov edx,[__access_address]\n"); emit("ret\n");}static void gen_readl(void){ align(16); emit("readmemory%s:\n",sizename[4]); emit("mov [__access_address],edx\n"); maskaddress("edx"); emit("mov ecx,[__readword]\n"); emit("readl_check:\n"); emit("cmp edx,[ecx]\n"); /* Are we smaller? */ emit("jb short readl_next\n"); /* Yes, go to next address */ emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */ emit("jbe short readl_call\n"); emit("readl_next:\n"); emit("cmp dword[ecx],byte -1\n");/* End of list? */ emit("je short readl_outofrange\n"); emit("add ecx,byte 16\n"); /* To the next structure */ emit("jmp short readl_check\n"); emit("readl_outofrange:\n");#ifndef RAINE emit("add edx,byte 2\n"); emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */#endif emit("mov ecx,-1\n");#ifndef RAINE emit("ja near readl_lower\n");#endif emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("readl_call:\n"); emit("cmp dword[ecx+8],byte 0\n"); emit("jne short readl_callio\n");#ifndef RAINE emit("add edx,byte 2\n"); emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */ emit("ja short readl_split\n");#endif /* Unsplit version */#ifndef RAINE emit("sub edx,[ecx]\n");#endif emit("add edx,[ecx+12]\n");#ifndef RAINE emit("mov ecx,[edx-2]\n");#else emit("mov ecx,[edx]\n");#endif emit("rol ecx,16\n"); emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("readl_callio:\n");#ifndef RAINE emit("add edx,byte 2\n"); emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */ emit("ja near readl_iosplit\n"); emit("sub edx,byte 2\n");#endif /* Unsplit version */ airlock_exit(); emit("mov eax,edx\n"); /* address */ emit("mov edx,ecx\n"); /* pointer to structure */ emit("push eax\n"); emit("push edx\n"); if(use_stack){ emit("push edx\n"); emit("push eax\n"); } emit("call dword[edx+8]\n"); if(use_stack)emit("add esp,byte 8\n"); emit("pop edx\n"); emit("xchg eax,[esp]\n"); emit("add eax,byte 2\n");/* maskaddress("eax");*/ /* this case would force a split read anyway */ if(use_stack){ emit("push edx\n"); emit("push eax\n"); } emit("call dword[edx+8]\n"); if(use_stack)emit("add esp,byte 8\n"); emit("pop ecx\n"); emit("shl ecx,16\n"); emit("mov cx,ax\n"); airlock_enter(); emit("mov edx,[__access_address]\n"); emit("ret\n");#ifndef RAINE emit("readl_split:\n"); emit("sub edx,[ecx]\n"); emit("add edx,[ecx+12]\n"); emit("mov cx,[edx-2]\n"); emit("readl_lower:\n"); emit("mov edx,[esp]\n"); emit("add edx,byte 2\n"); emit("shl ecx,16\n"); emit("push ecx\n"); emit("call readmemoryword\n"); emit("and ecx,0FFFFh\n"); emit("or ecx,[esp]\n"); emit("add esp,byte 4\n"); emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("readl_iosplit:\n"); emit("sub edx,byte 2\n"); airlock_exit(); emit("mov eax,edx\n"); /* address */ emit("mov edx,ecx\n"); /* pointer to structure */ if(use_stack){ emit("push edx\n"); emit("push eax\n"); } emit("call dword[edx+8]\n"); if(use_stack)emit("add esp,byte 8\n"); emit("mov ecx,eax\n"); airlock_enter(); emit("jmp short readl_lower\n");#endif}static void gen_writebw(int size){ char z='x'; if(size==1)z='b'; if(size==2)z='w'; align(16); emit("writememory%s:\n",sizename[size]); emit("mov [__access_address],edx\n"); emit("push ecx\n"); emit("write%c_top:\n",z); maskaddress("edx"); emit("mov ecx,[__write%s]\n",sizename[size]); emit("write%c_check:\n",z); emit("cmp edx,[ecx]\n"); /* Are we smaller? */ emit("jb short write%c_next\n",z); /* Yes, go to next address */ emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */ emit("jbe short write%c_call\n",z); emit("write%c_next:\n",z); emit("cmp dword[ecx],byte -1\n");/* End of list? */ emit("je short write%c_end\n",z); emit("add ecx,byte 16\n"); /* To the next structure */ emit("jmp short write%c_check\n",z); emit("write%c_call:\n",z); emit("cmp dword[ecx+8],byte 0\n"); emit("jne short write%c_callio\n",z);#ifndef RAINE emit("sub edx,[ecx]\n");#endif emit("add edx,[ecx+12]\n"); if(z=='b')emit("xor edx,byte 1\n"); emit("pop ecx\n"); emit("mov [edx],%s\n",x86cx[size]); emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("write%c_callio:\n",z); /* --- we have: ** index in ecx ** address in edx ** value in [esp] ** --- we want: ** index in anything (saved first) ** address in eax ** value in edx */ airlock_exit(); emit("mov ebx,ecx\n"); /* pointer to structure */ emit("mov eax,edx\n"); /* address */ emit("xor edx,edx\n"); /* data */ emit("mov %s,[esp+%d]\n",x86dx[size],airlock_stacksize); if(use_stack){ emit("push ebx\n"); emit("push edx\n"); emit("push eax\n"); } emit("call dword[ebx+8]\n"); if(use_stack)emit("add esp,byte 12\n"); airlock_enter(); emit("write%c_end:\n",z); emit("pop ecx\n"); emit("mov edx,[__access_address]\n"); emit("ret\n");}static void gen_writel(void){ align(16); emit("writememory%s:\n",sizename[4]); emit("mov [__access_address],edx\n"); emit("push ecx\n"); maskaddress("edx"); emit("mov ecx,[__write%s]\n",sizename[2]); emit("writel_check:\n"); emit("cmp edx,[ecx]\n"); /* Are we smaller? */ emit("jb short writel_next\n"); /* Yes, go to next address */ emit("cmp edx,[ecx+4]\n"); /* Are we bigger? */ emit("jbe short writel_call\n"); emit("writel_next:\n"); emit("cmp dword[ecx],byte -1\n");/* End of list? */#ifndef RAINE emit("je short writel_outofrange\n");#else emit("je short writel_end\n");#endif emit("add ecx,byte 16\n"); /* To the next structure */ emit("jmp short writel_check\n"); /* The top word was out of range, but the bottom word might not be */#ifndef RAINE emit("writel_outofrange:\n"); emit("add edx,byte 2\n"); emit("jmp writew_top\n");#endif emit("writel_call:\n"); emit("cmp dword[ecx+8],byte 0\n"); emit("jne short writel_callio\n");#ifndef RAINE emit("add edx,byte 2\n"); emit("cmp edx,[ecx+4]\n"); emit("ja short writel_split\n"); emit("sub edx,[ecx]\n");#endif emit("add edx,[ecx+12]\n");#ifndef RAINE emit("pop ecx\n");#else emit("mov ecx,[esp]\n");#endif emit("rol ecx,16\n");#ifndef RAINE emit("mov [edx-2],ecx\n");#else emit("mov [edx],ecx\n"); emit("pop ecx\n");#endif emit("mov edx,[__access_address]\n"); emit("ret\n"); emit("writel_callio:\n");#ifndef RAINE emit("add edx,byte 2\n"); emit("cmp edx,[ecx+4]\n"); emit("ja short writel_iosplit\n"); emit("sub edx,byte 2\n");#endif /* Unsplit version */ /* --- we have: ** index in ecx ** address in edx ** value in [esp] ** --- we want: ** index in anything (saved first) ** address in eax ** value in edx */ airlock_exit(); emit("mov ebx,ecx\n"); /* pointer to structure */ emit("mov eax,edx\n"); /* address */ emit("xor edx,edx\n"); /* data */ emit("mov dx,[esp+%d]\n",airlock_stacksize+2); emit("push eax\n"); emit("push ebx\n"); if(use_stack){ emit("push ebx\n"); emit("push edx\n"); emit("push eax\n"); } emit("call dword[ebx+8]\n"); if(use_stack)emit("add esp,byte 12\n"); emit("pop ebx\n"); emit("pop eax\n"); emit("add eax,byte 2\n");/* maskaddress("eax");*/ /*this case would force a split write anyway */ emit("xor edx,edx\n"); /* data */ emit("mov dx,[esp+%d]\n",airlock_stacksize); if(use_stack){ emit("push ebx\n"); emit("push edx\n"); emit("push eax\n"); } emit("call dword[ebx+8]\n"); if(use_stack)emit("add esp,byte 12\n"); airlock_enter(); emit("writel_end:\n"); emit("pop ecx\n"); emit("mov edx,[__access_address]\n"); emit("ret\n");#ifndef RAINE emit("writel_split:\n"); emit("sub edx,[ecx]\n"); emit("add edx,[ecx+12]\n"); emit("mov cx,[esp+2]\n"); emit("mov [edx-2],cx\n"); emit("mov edx,[esp+4]\n"); emit("add edx,byte 2\n"); emit("jmp writew_top\n"); emit("writel_iosplit:\n"); /* --- we have: ** index in ecx ** address in edx ** value in [esp] ** --- we want: ** index in anything (saved first) ** address in eax ** value in edx */ airlock_exit(); emit("mov ebx,ecx\n"); /* pointer to structure */ emit("mov eax,edx\n"); /* address */ emit("xor edx,edx\n"); /* data */ emit("mov dx,[esp+%d]\n",airlock_stacksize+2); if(use_stack){ emit("push ebx\n"); emit("push edx\n"); emit("push eax\n"); } emit("call dword[ebx+8]\n"); if(use_stack)emit("add esp,byte 12\n"); airlock_enter(); emit("mov edx,[esp+4]\n"); emit("add edx,byte 2\n"); emit("jmp writew_top\n");#endif}/***************************************************************************//*** Group 1 and 2 exceptions** Exception address is passed in EDX**** Does not fix the new PC!*/static void gen_group_12_exception(void) { align(16); emit("group_1_exception:\n"); emit("group_2_exception:\n"); emit("and byte[__interrupts],0FEh\n"); /* first thing's first */ if(cputype == 68010) { emit("mov byte[__loopmode],0\n"); } if(cputype >= 68010) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -