mirror of
https://github.com/cc65/cc65.git
synced 2025-02-03 22:32:24 +00:00
More funcinfo on register usage fixes.
This commit is contained in:
parent
fe003eedd4
commit
0bfa13722b
@ -172,6 +172,10 @@ static void SetUseChgInfo (CodeEntry* E, const OPCDesc* D)
|
||||
if (Info && Info->ByteUse != REG_NONE) {
|
||||
/* These addressing modes will never change the zp loc */
|
||||
E->Use |= Info->WordUse;
|
||||
|
||||
if ((E->Use & REG_SP) != 0) {
|
||||
E->Use |= SLV_IND;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -82,269 +82,296 @@ struct FuncInfo {
|
||||
unsigned Chg; /* Changed/destroyed registers */
|
||||
};
|
||||
|
||||
/* Note for the shift functions: Shifts are done modulo 32, so all shift
|
||||
/* Functions that change the SP are regarded as using the SP as well.
|
||||
** The callax/jmpvec functions may call a function that uses/changes more
|
||||
** registers, so we should further check the info of the called function
|
||||
** or just play it safe.
|
||||
** Note for the shift functions: Shifts are done modulo 32, so all shift
|
||||
** routines are marked to use only the A register. The remainder is ignored
|
||||
** anyway.
|
||||
*/
|
||||
static const FuncInfo FuncInfoTable[] = {
|
||||
{ "addeq0sp", REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "addeqysp", REG_AXY, PSTATE_ALL | REG_AXY },
|
||||
{ "addysp", REG_Y, PSTATE_ALL | REG_NONE },
|
||||
{ "aslax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslaxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "asleax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asleax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asleax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asleax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "asrax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asrax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asrax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asrax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asraxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "asreax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asreax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asreax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asreax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "bcasta", REG_A, PSTATE_ALL | REG_AX },
|
||||
{ "bcastax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "bcasteax", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "bnega", REG_A, PSTATE_ALL | REG_AX },
|
||||
{ "bnegax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "bnegeax", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "booleq", PSTATE_Z, PSTATE_ALL | REG_AX },
|
||||
{ "boolge", PSTATE_N, PSTATE_ALL | REG_AX },
|
||||
{ "boolgt", PSTATE_ZN, PSTATE_ALL | REG_AX },
|
||||
{ "boolle", PSTATE_ZN, PSTATE_ALL | REG_AX },
|
||||
{ "boollt", PSTATE_N, PSTATE_ALL | REG_AX },
|
||||
{ "boolne", PSTATE_Z, PSTATE_ALL | REG_AX },
|
||||
{ "booluge", PSTATE_C, PSTATE_ALL | REG_AX },
|
||||
{ "boolugt", PSTATE_CZ, PSTATE_ALL | REG_AX },
|
||||
{ "boolule", PSTATE_CZ, PSTATE_ALL | REG_AX },
|
||||
{ "boolult", PSTATE_C, PSTATE_ALL | REG_AX },
|
||||
{ "callax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "complax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax1", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax2", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax3", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax4", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax5", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax6", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax7", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax8", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decaxy", REG_AXY, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "deceaxy", REG_EAXY, PSTATE_ALL | REG_EAX },
|
||||
{ "decsp1", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "decsp2", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "decsp3", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "decsp4", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "decsp5", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "decsp6", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "decsp7", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "decsp8", REG_NONE, PSTATE_ALL | REG_A },
|
||||
{ "incax1", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "incax2", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "incax3", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax4", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax5", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax6", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax7", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax8", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incaxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incsp1", REG_NONE, PSTATE_ALL | REG_NONE },
|
||||
{ "incsp2", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "incsp3", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "incsp4", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "incsp5", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "incsp6", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "incsp7", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "incsp8", REG_NONE, PSTATE_ALL | REG_Y },
|
||||
{ "laddeq", REG_EAXY|REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "laddeq0sp", REG_EAX, PSTATE_ALL | REG_EAXY },
|
||||
{ "laddeq1", REG_Y | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "laddeqa", REG_AY | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "laddeqysp", REG_EAXY, PSTATE_ALL | REG_EAXY },
|
||||
{ "ldaidx", REG_AXY, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "ldauidx", REG_AXY, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "ldax0sp", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "ldaxi", REG_AX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "ldaxidx", REG_AXY, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "ldaxysp", REG_Y, PSTATE_ALL | REG_AXY },
|
||||
{ "ldeax0sp", REG_NONE, PSTATE_ALL | REG_EAXY },
|
||||
{ "ldeaxi", REG_AX, PSTATE_ALL | REG_EAXY | REG_PTR1 },
|
||||
{ "ldeaxidx", REG_AXY, PSTATE_ALL | REG_EAXY | REG_PTR1 },
|
||||
{ "ldeaxysp", REG_Y, PSTATE_ALL | REG_EAXY },
|
||||
{ "leaa0sp", REG_A, PSTATE_ALL | REG_AX },
|
||||
{ "leaaxsp", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "lsubeq", REG_EAXY|REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "lsubeq0sp", REG_EAX, PSTATE_ALL | REG_EAXY },
|
||||
{ "lsubeq1", REG_Y | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "lsubeqa", REG_AY | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "lsubeqysp", REG_EAXY, PSTATE_ALL | REG_EAXY },
|
||||
{ "mulax10", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax3", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax5", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax6", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax7", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax9", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "negax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "push0", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push0ax", REG_AX, PSTATE_ALL | REG_Y | REG_SREG },
|
||||
{ "push1", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push2", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push3", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push4", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push5", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push6", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "push7", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "pusha", REG_A, PSTATE_ALL | REG_Y },
|
||||
{ "pusha0", REG_A, PSTATE_ALL | REG_XY },
|
||||
{ "pusha0sp", REG_NONE, PSTATE_ALL | REG_AY },
|
||||
{ "pushaFF", REG_A, PSTATE_ALL | REG_Y },
|
||||
{ "pushax", REG_AX, PSTATE_ALL | REG_Y },
|
||||
{ "pushaysp", REG_Y, PSTATE_ALL | REG_AY },
|
||||
{ "pushc0", REG_NONE, PSTATE_ALL | REG_A | REG_Y },
|
||||
{ "pushc1", REG_NONE, PSTATE_ALL | REG_A | REG_Y },
|
||||
{ "pushc2", REG_NONE, PSTATE_ALL | REG_A | REG_Y },
|
||||
{ "pusheax", REG_EAX, PSTATE_ALL | REG_Y },
|
||||
{ "pushl0", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "pushw", REG_AX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "pushw0sp", REG_NONE, PSTATE_ALL | REG_AXY },
|
||||
{ "pushwidx", REG_AXY, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "pushwysp", REG_Y, PSTATE_ALL | REG_AXY },
|
||||
{ "regswap", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "regswap1", REG_XY, PSTATE_ALL | REG_A },
|
||||
{ "regswap2", REG_XY, PSTATE_ALL | REG_A | REG_Y },
|
||||
{ "return0", REG_NONE, PSTATE_ALL | REG_AX },
|
||||
{ "return1", REG_NONE, PSTATE_ALL | REG_AX },
|
||||
{ "shlax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlaxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "shleax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shleax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shleax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shleax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "shrax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shrax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shrax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shrax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shraxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "shreax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shreax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shreax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shreax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "staspidx", REG_A | REG_Y, PSTATE_ALL | REG_Y | REG_TMP1 | REG_PTR1 },
|
||||
{ "stax0sp", REG_AX, PSTATE_ALL | REG_Y },
|
||||
{ "staxspidx", REG_AXY, PSTATE_ALL | REG_TMP1 | REG_PTR1 },
|
||||
{ "staxysp", REG_AXY, PSTATE_ALL | REG_Y },
|
||||
{ "steax0sp", REG_EAX, PSTATE_ALL | REG_Y },
|
||||
{ "steaxysp", REG_EAXY, PSTATE_ALL | REG_Y },
|
||||
{ "subeq0sp", REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "subeqysp", REG_AXY, PSTATE_ALL | REG_AXY },
|
||||
{ "subysp", REG_Y, PSTATE_ALL | REG_AY },
|
||||
{ "tosadd0ax", REG_AX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosadda0", REG_A, PSTATE_ALL | REG_AXY },
|
||||
{ "tosaddax", REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "tosaddeax", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosand0ax", REG_AX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosanda0", REG_A, PSTATE_ALL | REG_AXY },
|
||||
{ "tosandax", REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "tosandeax", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosaslax", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosasleax", REG_A, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosasrax", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosasreax", REG_A, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosdiv0ax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosdiva0", REG_A, PSTATE_ALL | REG_ALL },
|
||||
{ "tosdivax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosdiveax", REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "toseq00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toseqa0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toseqax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toseqeax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosge00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosgea0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosgeax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosgeeax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosgt00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosgta0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosgtax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosgteax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosicmp", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosicmp0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toslcmp", REG_EAX, PSTATE_ALL | REG_A | REG_Y | REG_PTR1 },
|
||||
{ "tosle00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toslea0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosleax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosleeax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "toslt00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toslta0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosltax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "toslteax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosmod0ax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmodeax", REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmul0ax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmula0", REG_A, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmulax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmuleax", REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosne00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosnea0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosneax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosneeax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosor0ax", REG_AX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosora0", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosorax", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosoreax", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosrsub0ax", REG_AX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosrsuba0", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosrsubax", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosrsubeax", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosshlax", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosshleax", REG_A, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosshrax", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosshreax", REG_A, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tossub0ax", REG_AX, PSTATE_ALL | REG_EAXY },
|
||||
{ "tossuba0", REG_A, PSTATE_ALL | REG_AXY },
|
||||
{ "tossubax", REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "tossubeax", REG_EAX, PSTATE_ALL | REG_EAXY },
|
||||
{ "tosudiv0ax", REG_AX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosudiva0", REG_A, PSTATE_ALL | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosudivax", REG_AX, PSTATE_ALL | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosudiveax", REG_EAX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosuge00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosugea0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosugeax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosugeeax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosugt00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosugta0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosugtax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosugteax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosule00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosulea0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosuleax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosuleeax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosult00", REG_NONE, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosulta0", REG_A, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosultax", REG_AX, PSTATE_ALL | REG_AXY | REG_SREG },
|
||||
{ "tosulteax", REG_EAX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "tosumod0ax", REG_AX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosumoda0", REG_A, PSTATE_ALL | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosumodax", REG_AX, PSTATE_ALL | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosumodeax", REG_EAX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosumul0ax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosumula0", REG_A, PSTATE_ALL | REG_ALL },
|
||||
{ "tosumulax", REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosumuleax", REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosxor0ax", REG_AX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tosxora0", REG_A, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosxorax", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "tosxoreax", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "tsteax", REG_EAX, PSTATE_ALL | REG_Y },
|
||||
{ "utsteax", REG_EAX, PSTATE_ALL | REG_Y },
|
||||
{ "addeq0sp", SLV_TOP | REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "addeqysp", SLV_IND | REG_AXY, PSTATE_ALL | REG_AXY },
|
||||
{ "addysp", REG_SP | REG_Y, PSTATE_ALL | REG_SP },
|
||||
{ "along", REG_A, PSTATE_ALL | REG_X | REG_SREG },
|
||||
{ "aslax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "aslaxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "asleax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asleax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asleax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asleax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "asrax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asrax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asrax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asrax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "asraxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "asreax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asreax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asreax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "asreax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "aulong", REG_NONE, PSTATE_ALL | REG_X | REG_SREG },
|
||||
{ "axlong", REG_X, PSTATE_ALL | REG_Y | REG_SREG },
|
||||
{ "axulong", REG_NONE, PSTATE_ALL | REG_Y | REG_SREG },
|
||||
{ "bcasta", REG_A, PSTATE_ALL | REG_AX },
|
||||
{ "bcastax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "bcasteax", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "bnega", REG_A, PSTATE_ALL | REG_AX },
|
||||
{ "bnegax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "bnegeax", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "booleq", PSTATE_Z, PSTATE_ALL | REG_AX },
|
||||
{ "boolge", PSTATE_N, PSTATE_ALL | REG_AX },
|
||||
{ "boolgt", PSTATE_ZN, PSTATE_ALL | REG_AX },
|
||||
{ "boolle", PSTATE_ZN, PSTATE_ALL | REG_AX },
|
||||
{ "boollt", PSTATE_N, PSTATE_ALL | REG_AX },
|
||||
{ "boolne", PSTATE_Z, PSTATE_ALL | REG_AX },
|
||||
{ "booluge", PSTATE_C, PSTATE_ALL | REG_AX },
|
||||
{ "boolugt", PSTATE_CZ, PSTATE_ALL | REG_AX },
|
||||
{ "boolule", PSTATE_CZ, PSTATE_ALL | REG_AX },
|
||||
{ "boolult", PSTATE_C, PSTATE_ALL | REG_AX },
|
||||
{ "callax", REG_AX, PSTATE_ALL | REG_ALL }, /* PSTATE_ZN | REG_PTR1 */
|
||||
{ "complax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax1", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax2", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax3", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax4", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax5", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax6", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax7", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decax8", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "decaxy", REG_AXY, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "deceaxy", REG_EAXY, PSTATE_ALL | REG_EAX },
|
||||
{ "decsp1", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "decsp2", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "decsp3", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "decsp4", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "decsp5", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "decsp6", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "decsp7", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "decsp8", REG_SP, PSTATE_ALL | REG_SP | REG_A },
|
||||
{ "enter", REG_SP | REG_Y, PSTATE_ALL | REG_SP | REG_AY },
|
||||
{ "incax1", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "incax2", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "incax3", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax4", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax5", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax6", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax7", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incax8", REG_AX, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incaxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "incsp1", REG_SP, PSTATE_ALL | REG_SP },
|
||||
{ "incsp2", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "incsp3", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "incsp4", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "incsp5", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "incsp6", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "incsp7", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "incsp8", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "jmpvec", REG_EVERYTHING, PSTATE_ALL | REG_ALL }, /* NONE */
|
||||
{ "laddeq", REG_EAXY | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "laddeq0sp", SLV_TOP | REG_EAX, PSTATE_ALL | REG_EAXY },
|
||||
{ "laddeq1", REG_Y | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "laddeqa", REG_AY | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "laddeqysp", SLV_IND | REG_EAXY, PSTATE_ALL | REG_EAXY },
|
||||
{ "ldaidx", REG_AXY, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "ldauidx", REG_AXY, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "ldax0sp", SLV_TOP, PSTATE_ALL | REG_AXY },
|
||||
{ "ldaxi", REG_AX, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "ldaxidx", REG_AXY, PSTATE_ALL | REG_AXY | REG_PTR1 },
|
||||
{ "ldaxysp", SLV_IND | REG_Y, PSTATE_ALL | REG_AXY },
|
||||
{ "ldeax0sp", SLV_TOP, PSTATE_ALL | REG_EAXY },
|
||||
{ "ldeaxi", REG_AX, PSTATE_ALL | REG_EAXY | REG_PTR1 },
|
||||
{ "ldeaxidx", REG_AXY, PSTATE_ALL | REG_EAXY | REG_PTR1 },
|
||||
{ "ldeaxysp", SLV_IND | REG_Y, PSTATE_ALL | REG_EAXY },
|
||||
{ "leaa0sp", REG_SP | REG_A, PSTATE_ALL | REG_AX },
|
||||
{ "leaaxsp", REG_SP | REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "leave00", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "leave0", REG_SP, PSTATE_ALL | REG_SP | REG_XY },
|
||||
{ "leave", REG_SP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "leavey00", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "leavey0", REG_SP, PSTATE_ALL | REG_SP | REG_XY },
|
||||
{ "leavey", REG_SP | REG_Y, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "lsubeq", REG_EAXY | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "lsubeq0sp", SLV_TOP | REG_EAX, PSTATE_ALL | REG_EAXY },
|
||||
{ "lsubeq1", REG_Y | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "lsubeqa", REG_AY | REG_PTR1_LO, PSTATE_ALL | REG_EAXY | REG_PTR1_HI },
|
||||
{ "lsubeqysp", SLV_IND | REG_EAXY, PSTATE_ALL | REG_EAXY },
|
||||
{ "mulax10", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax3", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax5", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax6", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax7", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "mulax9", REG_AX, PSTATE_ALL | REG_AX | REG_PTR1 },
|
||||
{ "negax", REG_AX, PSTATE_ALL | REG_AX },
|
||||
{ "negeax", REG_EAX, PSTATE_ALL | REG_EAX },
|
||||
{ "popa", SLV_TOP, PSTATE_ALL | REG_SP | REG_AY },
|
||||
{ "popax", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "popeax", SLV_TOP, PSTATE_ALL | REG_SP | REG_EAXY },
|
||||
{ "push0", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push0ax", REG_SP | REG_AX, PSTATE_ALL | REG_SP | REG_Y | REG_SREG },
|
||||
{ "push1", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push2", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push3", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push4", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push5", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push6", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "push7", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "pusha", REG_SP | REG_A, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "pusha0", REG_SP | REG_A, PSTATE_ALL | REG_SP | REG_XY },
|
||||
{ "pusha0sp", SLV_TOP, PSTATE_ALL | REG_SP | REG_AY },
|
||||
{ "pushaFF", REG_SP | REG_A, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "pushax", REG_SP | REG_AX, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "pushaysp", SLV_IND | REG_Y, PSTATE_ALL | REG_SP | REG_AY },
|
||||
{ "pushc0", REG_SP, PSTATE_ALL | REG_SP | REG_A | REG_Y },
|
||||
{ "pushc1", REG_SP, PSTATE_ALL | REG_SP | REG_A | REG_Y },
|
||||
{ "pushc2", REG_SP, PSTATE_ALL | REG_SP | REG_A | REG_Y },
|
||||
{ "pusheax", REG_SP | REG_EAX, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "pushl0", REG_SP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "pushw", REG_SP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "pushw0sp", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "pushwidx", REG_SP | REG_AXY, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "pushwysp", SLV_IND | REG_Y, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "regswap", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "regswap1", REG_XY, PSTATE_ALL | REG_A },
|
||||
{ "regswap2", REG_XY, PSTATE_ALL | REG_A | REG_Y },
|
||||
{ "resteax", REG_SAVE, PSTATE_ZN | REG_EAX }, /* also uses regsave+2/+3 */
|
||||
{ "return0", REG_NONE, PSTATE_ALL | REG_AX },
|
||||
{ "return1", REG_NONE, PSTATE_ALL | REG_AX },
|
||||
{ "saveeax", REG_EAX, PSTATE_ZN | REG_Y | REG_SAVE }, /* also regsave+2/+3 */
|
||||
{ "shlax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shlaxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "shleax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shleax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shleax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shleax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "shrax1", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shrax2", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shrax3", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shrax4", REG_AX, PSTATE_ALL | REG_AX | REG_TMP1 },
|
||||
{ "shraxy", REG_AXY, PSTATE_ALL | REG_AXY | REG_TMP1 },
|
||||
{ "shreax1", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shreax2", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shreax3", REG_EAX, PSTATE_ALL | REG_EAX | REG_TMP1 },
|
||||
{ "shreax4", REG_EAX, PSTATE_ALL | REG_EAXY | REG_TMP1 },
|
||||
{ "staspidx", SLV_TOP | REG_AY, PSTATE_ALL | REG_SP | REG_Y | REG_TMP1 | REG_PTR1 },
|
||||
{ "stax0sp", REG_SP | REG_AX, PSTATE_ALL | SLV_TOP | REG_Y },
|
||||
{ "staxspidx", SLV_TOP | REG_AXY, PSTATE_ALL | REG_SP | REG_TMP1 | REG_PTR1 },
|
||||
{ "staxysp", REG_SP | REG_AXY, PSTATE_ALL | SLV_IND | REG_Y },
|
||||
{ "steax0sp", REG_SP | REG_EAX, PSTATE_ALL | SLV_TOP | REG_Y },
|
||||
{ "steaxspidx", SLV_TOP | REG_EAXY, PSTATE_ALL | REG_SP | REG_Y | REG_TMP1 | REG_PTR1 }, /* also tmp2, tmp3 */
|
||||
{ "steaxysp", REG_SP | REG_EAXY, PSTATE_ALL | SLV_IND | REG_Y },
|
||||
{ "subeq0sp", SLV_TOP | REG_AX, PSTATE_ALL | REG_AXY },
|
||||
{ "subeqysp", SLV_IND | REG_AXY, PSTATE_ALL | REG_AXY },
|
||||
{ "subysp", REG_SP | REG_Y, PSTATE_ALL | REG_SP | REG_AY },
|
||||
{ "swapstk", SLV_TOP | REG_AX, PSTATE_ALL | SLV_TOP | REG_AXY }, /* also ptr4 */
|
||||
{ "tosadd0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosadda0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "tosaddax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "tosaddeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosand0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosanda0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "tosandax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "tosandeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosaslax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosasleax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosasrax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosasreax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosdiv0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_ALL },
|
||||
{ "tosdiva0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_ALL },
|
||||
{ "tosdivax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_ALL },
|
||||
{ "tosdiveax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_ALL },
|
||||
{ "toseq00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "toseqa0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "toseqax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "toseqeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosge00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosgea0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosgeax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosgeeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosgt00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosgta0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosgtax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosgteax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosicmp", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosicmp0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosint", SLV_TOP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "toslcmp", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_A | REG_Y | REG_PTR1 },
|
||||
{ "tosle00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "toslea0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosleax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosleeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "toslong", SLV_TOP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "toslt00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "toslta0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosltax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "toslteax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosmod0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmodeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmul0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmula0", SLV_TOP | REG_A, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmulax", SLV_TOP | REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosmuleax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosne00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosnea0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosneax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosneeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosor0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosora0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosorax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosoreax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosrsub0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosrsuba0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosrsubax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosrsubeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosshlax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosshleax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosshrax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosshreax", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tossub0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY },
|
||||
{ "tossuba0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "tossubax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY },
|
||||
{ "tossubeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_EAXY },
|
||||
{ "tosudiv0ax", SLV_TOP | REG_AX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosudiva0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosudivax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosudiveax", SLV_TOP | REG_EAX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosuge00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosugea0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosugeax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosugeeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosugt00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosugta0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosugtax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosugteax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosule00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosulea0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosuleax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosuleeax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosulong", SLV_TOP, PSTATE_ALL | REG_SP | REG_Y },
|
||||
{ "tosult00", SLV_TOP, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosulta0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosultax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_SREG },
|
||||
{ "tosulteax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_AXY | REG_PTR1 },
|
||||
{ "tosumod0ax", SLV_TOP | REG_AX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosumoda0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosumodax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_PTR1 }, /* also ptr4 */
|
||||
{ "tosumodeax", SLV_TOP | REG_EAX, PSTATE_ALL | (REG_ALL & ~REG_SAVE) },
|
||||
{ "tosumul0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosumula0", SLV_TOP | REG_A, PSTATE_ALL | REG_ALL },
|
||||
{ "tosumulax", SLV_TOP | REG_AX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosumuleax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_ALL },
|
||||
{ "tosxor0ax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tosxora0", SLV_TOP | REG_A, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosxorax", SLV_TOP | REG_AX, PSTATE_ALL | REG_SP | REG_AXY | REG_TMP1 },
|
||||
{ "tosxoreax", SLV_TOP | REG_EAX, PSTATE_ALL | REG_SP | REG_EAXY | REG_TMP1 },
|
||||
{ "tsteax", REG_EAX, PSTATE_ALL | REG_Y },
|
||||
{ "utsteax", REG_EAX, PSTATE_ALL | REG_Y },
|
||||
};
|
||||
#define FuncInfoCount (sizeof(FuncInfoTable) / sizeof(FuncInfoTable[0]))
|
||||
|
||||
@ -481,6 +508,7 @@ fncls_t GetFuncInfo (const char* Name, unsigned int* Use, unsigned int* Chg)
|
||||
/* Did we find it in the top-level table? */
|
||||
if (E && IsTypeFunc (E->Type)) {
|
||||
FuncDesc* D = GetFuncDesc (E->Type);
|
||||
*Use = REG_NONE;
|
||||
|
||||
/* A variadic function will use the Y register (the parameter list
|
||||
** size is passed there). A fastcall function will use the A or A/X
|
||||
@ -488,31 +516,40 @@ fncls_t GetFuncInfo (const char* Name, unsigned int* Use, unsigned int* Chg)
|
||||
** we assume that any function will destroy all registers.
|
||||
*/
|
||||
if ((D->Flags & FD_VARIADIC) != 0) {
|
||||
*Use = REG_Y;
|
||||
*Use = REG_Y | REG_SP | SLV_TOP;
|
||||
} else if (D->Flags & FD_CALL_WRAPPER) {
|
||||
/* Wrappers may go to any functions, so mark them as using all
|
||||
** registers.
|
||||
*/
|
||||
*Use = REG_EAXY;
|
||||
} else if ((D->ParamCount > 0 || (D->Flags & FD_EMPTY) != 0) &&
|
||||
IsFastcallFunc (E->Type)) {
|
||||
} else if (D->ParamCount > 0 || (D->Flags & FD_EMPTY) != 0) {
|
||||
/* Will use registers depending on the last param. If the last
|
||||
** param has incomplete type, or if the function has not been
|
||||
** prototyped yet, just assume __EAX__.
|
||||
*/
|
||||
if (D->LastParam != 0) {
|
||||
switch (SizeOf (D->LastParam->Type)) {
|
||||
case 1u:
|
||||
*Use = REG_A;
|
||||
break;
|
||||
case 2u:
|
||||
*Use = REG_AX;
|
||||
break;
|
||||
default:
|
||||
*Use = REG_EAX;
|
||||
if (IsFastcallFunc (E->Type)) {
|
||||
if (D->LastParam != 0) {
|
||||
switch (SizeOf (D->LastParam->Type)) {
|
||||
case 1u:
|
||||
*Use = REG_A;
|
||||
break;
|
||||
case 2u:
|
||||
*Use = REG_AX;
|
||||
break;
|
||||
default:
|
||||
*Use = REG_EAX;
|
||||
}
|
||||
if (D->ParamCount > 1) {
|
||||
/* Passes other params on the stack */
|
||||
*Use |= REG_SP | SLV_TOP;
|
||||
}
|
||||
} else {
|
||||
/* We'll assume all */
|
||||
*Use = REG_EAX | REG_SP | SLV_TOP;
|
||||
}
|
||||
} else {
|
||||
*Use = REG_EAX;
|
||||
/* Passes all params on the stack */
|
||||
*Use = REG_SP | SLV_TOP;
|
||||
}
|
||||
} else {
|
||||
/* Will not use any registers */
|
||||
@ -551,6 +588,9 @@ fncls_t GetFuncInfo (const char* Name, unsigned int* Use, unsigned int* Chg)
|
||||
/* Use the information we have */
|
||||
*Use = Info->Use;
|
||||
*Chg = Info->Chg;
|
||||
if ((*Use & (SLV_TOP | SLV_IND)) != 0) {
|
||||
*Use |= REG_SP;
|
||||
}
|
||||
} else {
|
||||
/* It's an internal function we have no information for. If in
|
||||
** debug mode, output an additional warning, so we have a chance
|
||||
|
@ -75,6 +75,8 @@ struct RegContents;
|
||||
#define REG_SP_HI 0x2000U
|
||||
|
||||
/* Defines for some special register usage */
|
||||
#define SLV_IND 0x00010000U /* Accesses (sp),y */
|
||||
#define SLV_TOP 0x00020000U /* Accesses (sp),0 */
|
||||
#define SLV_SP65 0x00200000U /* Accesses 6502 stack pointer */
|
||||
#define SLV_PH65 0x00400000U /* Pushes onto 6502 stack */
|
||||
#define SLV_PL65 0x00800000U /* Pops from 6502 stack */
|
||||
@ -104,6 +106,7 @@ struct RegContents;
|
||||
#define REG_EAXY (REG_EAX | REG_Y)
|
||||
#define REG_ZP 0xFFF8U
|
||||
#define REG_ALL 0xFFFFU
|
||||
|
||||
#define PSTATE_CZ (PSTATE_C | PSTATE_Z)
|
||||
#define PSTATE_CZN (PSTATE_C | PSTATE_Z | PSTATE_N)
|
||||
#define PSTATE_CZVN (PSTATE_C | PSTATE_Z | PSTATE_V | PSTATE_N)
|
||||
|
@ -827,21 +827,28 @@ void AdjustStackOffset (StackOpData* D, unsigned Offs)
|
||||
|
||||
CodeEntry* E = CS_GetEntry (D->Code, I);
|
||||
|
||||
/* Check against some things that should not happen */
|
||||
CHECK ((E->Use & SLV_TOP) != SLV_TOP);
|
||||
|
||||
/* Check if this entry does a stack access, and if so, if it's a plain
|
||||
** load from stack, since this is needed later.
|
||||
*/
|
||||
int Correction = 0;
|
||||
if ((E->Use & REG_SP) != 0) {
|
||||
if ((E->Use & SLV_IND) == SLV_IND) {
|
||||
|
||||
/* Check for some things that should not happen */
|
||||
CHECK (E->AM == AM65_ZP_INDY || E->RI->In.RegY >= (short) Offs);
|
||||
CHECK (strcmp (E->Arg, "sp") == 0);
|
||||
/* We need to correct this one */
|
||||
Correction = (E->OPC == OP65_LDA)? 2 : 1;
|
||||
if (E->OPC != OP65_JSR) {
|
||||
/* Check against some things that should not happen */
|
||||
CHECK (E->AM == AM65_ZP_INDY && E->RI->In.RegY >= (short) Offs);
|
||||
CHECK (strcmp (E->Arg, "sp") == 0);
|
||||
|
||||
/* We need to correct this one */
|
||||
Correction = 2;
|
||||
|
||||
} else {
|
||||
/* We need to correct this one */
|
||||
Correction = 1;
|
||||
}
|
||||
|
||||
} else if (CE_IsCallTo (E, "ldaxysp")) {
|
||||
/* We need to correct this one */
|
||||
Correction = 1;
|
||||
}
|
||||
|
||||
if (Correction) {
|
||||
@ -849,7 +856,7 @@ void AdjustStackOffset (StackOpData* D, unsigned Offs)
|
||||
** value.
|
||||
*/
|
||||
CodeEntry* P = CS_GetPrevEntry (D->Code, I);
|
||||
if (P && P->OPC == OP65_LDY && CE_IsConstImm (P)) {
|
||||
if (P && P->OPC == OP65_LDY && CE_IsConstImm (P) && !CE_HasLabel (E)) {
|
||||
/* The Y load is just before the stack access, adjust it */
|
||||
CE_SetNumArg (P, P->Num - Offs);
|
||||
} else {
|
||||
@ -860,39 +867,59 @@ void AdjustStackOffset (StackOpData* D, unsigned Offs)
|
||||
}
|
||||
|
||||
/* If we need the value of Y later, be sure to reload it */
|
||||
if (RegYUsed (D->Code, I+1)) {
|
||||
CodeEntry* N;
|
||||
unsigned R = REG_Y | (E->Chg & ~REG_A);
|
||||
R = GetRegInfo (D->Code, I + 1, R) & R;
|
||||
if ((R & REG_Y) != 0) {
|
||||
const char* Arg = MakeHexArg (E->RI->In.RegY);
|
||||
if (Correction == 2 && (N = CS_GetNextEntry(D->Code, I)) != 0 &&
|
||||
((N->Info & OF_ZBRA) != 0) && N->JumpTo != 0) {
|
||||
/* The Y register is used but the load instruction loads A
|
||||
** and is followed by a branch that evaluates the zero flag.
|
||||
** This means that we cannot just insert the load insn
|
||||
** for the Y register at this place, because it would
|
||||
** destroy the Z flag. Instead place load insns at the
|
||||
** target of the branch and after it.
|
||||
** Note: There is a chance that this code won't work. The
|
||||
** jump may be a backwards jump (in which case the stack
|
||||
** offset has already been adjusted) or there may be other
|
||||
** instructions between the load and the conditional jump.
|
||||
** Currently the compiler does not generate such code, but
|
||||
** it is possible to force the optimizer into something
|
||||
** invalid by use of inline assembler.
|
||||
*/
|
||||
if ((R & PSTATE_ZN) != 0 && (R & ~(REG_Y | PSTATE_ZN)) == 0) {
|
||||
CodeEntry* N;
|
||||
if ((N = CS_GetNextEntry (D->Code, I)) != 0 &&
|
||||
((N->Info & OF_ZBRA) != 0) && N->JumpTo != 0) {
|
||||
/* The Y register is used but the load instruction loads A
|
||||
** and is followed by a branch that evaluates the zero flag.
|
||||
** This means that we cannot just insert the load insn
|
||||
** for the Y register at this place, because it would
|
||||
** destroy the Z flag. Instead place load insns at the
|
||||
** target of the branch and after it.
|
||||
** Note: There is a chance that this code won't work. The
|
||||
** jump may be a backwards jump (in which case the stack
|
||||
** offset has already been adjusted) or there may be other
|
||||
** instructions between the load and the conditional jump.
|
||||
** Currently the compiler does not generate such code, but
|
||||
** it is possible to force the optimizer into something
|
||||
** invalid by use of inline assembler.
|
||||
** Note: In reality, this route is never taken as all
|
||||
** callers of this function will just give up with
|
||||
** optimization whenever they detect a branch.
|
||||
*/
|
||||
|
||||
/* Add load insn after the branch */
|
||||
CodeEntry* X = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, E->LI);
|
||||
InsertEntry (D, X, I+2);
|
||||
/* Add load insn after the branch */
|
||||
CodeEntry* X = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, E->LI);
|
||||
InsertEntry (D, X, I+2);
|
||||
|
||||
/* Add load insn before branch target */
|
||||
CodeEntry* Y = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, E->LI);
|
||||
int J = CS_GetEntryIndex (D->Code, N->JumpTo->Owner);
|
||||
CHECK (J > I); /* Must not happen */
|
||||
InsertEntry (D, Y, J);
|
||||
/* Add load insn before branch target */
|
||||
CodeEntry* Y = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, E->LI);
|
||||
int J = CS_GetEntryIndex (D->Code, N->JumpTo->Owner);
|
||||
CHECK (J > I); /* Must not happen */
|
||||
InsertEntry (D, Y, J);
|
||||
|
||||
/* Move the label to the new insn */
|
||||
CodeLabel* L = CS_GenLabel (D->Code, Y);
|
||||
CS_MoveLabelRef (D->Code, N, L);
|
||||
/* Move the label to the new insn */
|
||||
CodeLabel* L = CS_GenLabel (D->Code, Y);
|
||||
CS_MoveLabelRef (D->Code, N, L);
|
||||
|
||||
/* Skip the next two instructions in the next round */
|
||||
I += 2;
|
||||
} else {
|
||||
/* This could be suboptimal but it will always work (unless stack overflows) */
|
||||
CodeEntry* X = NewCodeEntry (OP65_PHP, AM65_IMP, 0, 0, E->LI);
|
||||
InsertEntry (D, X, I+1);
|
||||
X = NewCodeEntry (OP65_LDY, AM65_IMM, 0, 0, E->LI);
|
||||
InsertEntry (D, X, I+2);
|
||||
X = NewCodeEntry (OP65_PLP, AM65_IMP, 0, 0, E->LI);
|
||||
InsertEntry (D, X, I+3);
|
||||
/* Skip the three inserted instructions in the next round */
|
||||
I += 3;
|
||||
}
|
||||
} else {
|
||||
CodeEntry* X = NewCodeEntry (OP65_LDY, AM65_IMM, Arg, 0, E->LI);
|
||||
InsertEntry (D, X, I+1);
|
||||
|
Loading…
x
Reference in New Issue
Block a user