hschumann2/TempleOS-Source-Code
0838
1 2asm {3#assert !((REGG_LOCAL_NON_PTR_VARS|REGG_LOCAL_VARS)&~0xFCC0)4_TEST_EXCEPT::5 XOR RAX,RAX6 MOV RAX,FS:U64 CTask.last_except[RAX]7 MOV RBP,U64 CExcept.rbp[RAX]8 MOV RSI,U64 CExcept.rsi[RAX]9 MOV RDI,U64 CExcept.rdi[RAX]10 MOV R10,U64 CExcept.r10[RAX]11 MOV R11,U64 CExcept.r11[RAX]12 MOV R12,U64 CExcept.r12[RAX]13 MOV R13,U64 CExcept.r13[RAX]14 MOV R14,U64 CExcept.r14[RAX]15 MOV R15,U64 CExcept.r15[RAX]16 PUSH U64 CExcept.rflags[RAX]17 POPFD18 JMP U64 CExcept.hndlr_catch[RAX]19 20_TAKE_EXCEPT::21 XOR RAX,RAX22 MOV RAX,FS:U64 CTask.last_except[RAX]23 MOV RSP,U64 CExcept.rsp[RAX]24 JMP U64 CExcept.hndlr_untry[RAX]25 26_SAVE_EXCEPT_REGS::27 PUSH RBP28 MOV RBP,RSP29 MOV RAX,U64 SF_ARG1[RBP]30 MOV U64 CExcept.rsi[RAX],RSI31 MOV U64 CExcept.rdi[RAX],RDI32 MOV U64 CExcept.r10[RAX],R1033 MOV U64 CExcept.r11[RAX],R1134 MOV U64 CExcept.r12[RAX],R1235 MOV U64 CExcept.r13[RAX],R1336 MOV U64 CExcept.r14[RAX],R1437 MOV U64 CExcept.r15[RAX],R1538 POP RBP39 RET1 840}41 42_extern _TEST_EXCEPT U0 TestExcept();43_extern _TAKE_EXCEPT U0 TakeExcept();44_extern _SAVE_EXCEPT_REGS U0 SaveExceptRegs(CExcept *t);45 46U0 PutExcept(Bool catch_it=TRUE)47{//Print exception msg and catch exception.48 "Except:%c:",Fs->except_ch;49 "%P:%P:%P:%P:%P:%P\n",Fs->except_callers[0],Fs->except_callers[1],50 Fs->except_callers[2],Fs->except_callers[3],Fs->except_callers[4],51 Fs->except_callers[5],Fs->except_callers[6],Fs->except_callers[7];52 Fs->catch_except=catch_it;53}54 55#exe {Option(OPTf_NO_REG_VAR,ON);};56 57class CTryStk58{59 I64 rbp;60 I64 ret_rip;61 I64 arg1;62 I64 arg2;63};64 65U0 SysTry(U8 *catch_start,U8 *untry_start)66{67 I64 *rbp=GetRBP;68 CExcept *tmpt=MAlloc(sizeof(CExcept));69 tmpt->hndlr_catch=catch_start;70 tmpt->hndlr_untry=untry_start;71 tmpt->rsp=rbp(U8 *)+sizeof(CTryStk);72 tmpt->rbp=*rbp;73 tmpt->rflags=GetRFlags;74 SaveExceptRegs(tmpt);75 QueIns(tmpt,Fs->last_except);76}77 78U0 SysUntry()79{80 CExcept *tmpt=Fs->last_except;81 QueRem(tmpt);82 Free(tmpt);83}84 85U0 throw(I64 ch=0,Bool no_log=FALSE)86{//ch can be up to 8 chars like PutChars().87//In the catcher, fetch ch from Fs->except_ch.88 CExcept *tmpt=Fs->last_except;89 Bool was_raw;90 I64 i;91 Fs->except_ch=ch;92 for (i=0;i<TASK_EXCEPT_CALLERS;i++)93 Fs->except_callers[i]=Caller(i+1);94 Fs->except_rbp=GetRBP;95 Fs->catch_except=FALSE;96 if (!no_log)97 AdamLog("Except:%c:%p:%p:%p:%p:%p:%p\n",ch,Fs->except_callers[0],98 Fs->except_callers[1],Fs->except_callers[2],Fs->except_callers[3],99 Fs->except_callers[4],Fs->except_callers[5],Fs->except_callers[6],100 Fs->except_callers[7]);101 while (Fs->next_except!=&Fs->next_except) {102 TestExcept;103 if (Fs->catch_except)104 TakeExcept;105 SetRBP(Fs->except_rbp);106 tmpt=Fs->last_except;107 QueRem(tmpt);108 Free(tmpt);109 }110 was_raw=Raw(ON);111 PutExcept(FALSE);112 Panic("Unhandled Exception");113 Raw(was_raw);114}115 116#exe {Option(OPTf_NO_REG_VAR,OFF);};117 118U0 Break()119{//Send <CTRL-ALT-c>.120 if (Bt(&Fs->task_flags,TASKf_BREAK_TO_SHIFT_ESC))121 Msg(MSG_KEY_DOWN,CH_SHIFT_ESC,0x20100000201);122 else {123 Fs->wake_jiffy=0;124 TaskRstAwaitingMsg;125 DrvsRelease();126 BlkDevsRelease();127 FlushMsgs;128 throw('Break');129 }130}131 132Bool BreakLock(CTask *task=NULL)133{//Disables <CTRL-ALT-c>.134 if (!task) task=Fs;135 return !LBts(&task->task_flags,TASKf_BREAK_LOCKED);136}137 138Bool BreakUnlock(CTask *task=NULL)139{//Reenables <CTRL-ALT-c> and issues any pending breaks.140 Bool res;141 if (!task) task=Fs;142 res=LBtr(&task->task_flags,TASKf_BREAK_LOCKED);143 if (LBtr(&task->task_flags,TASKf_PENDING_BREAK)) {144 if (task==Fs)145 Break;146 else147 task->rip=&Break;148 }149 return res;150}151 