342 lines
5.8 KiB
C++
342 lines
5.8 KiB
C++
/*
|
||
$SP,"<1>",BI=1$
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
Tasks have symbol tables. If symbol not found, parent task's table
|
||
is searched. Adam task has system-wide symbols.
|
||
|
||
SYMBOL LOOK-UP (Especially, used by JIT compiler and Loader)
|
||
1) Symbol text name is hashed -- Adding the ASCII values of all
|
||
chars with shifts.
|
||
2) Hash body array is indexed.
|
||
3) Linked-lst is traversed until match of text and type-of-entry.
|
||
4) If not found, next hash table is searched.
|
||
|
||
Duplicate entries are allowed--they overshadow old entries.
|
||
|
||
ADDRESS-TO-SYMBOL LOOK-UP (Slow because not important--could add tree)
|
||
1) PSect Cache is scanned.
|
||
2) Hash Tables are scanned. See $LK,"PSectFind",A="MN:PSectFind"$().
|
||
*/
|
||
|
||
asm {
|
||
USE64
|
||
//************************************
|
||
SYS_HASH_STR::
|
||
// IN: RSI=Addr of string
|
||
// OUT: RAX
|
||
XOR RAX,RAX
|
||
TEST RSI,RSI
|
||
JZ @@15
|
||
|
||
PUSH RSI
|
||
PUSH RBX
|
||
XOR RBX,RBX
|
||
JMP @@10
|
||
|
||
@@05: SHL1 RBX
|
||
ADC RBX,RAX
|
||
@@10: LODSB
|
||
TEST AL,AL
|
||
JNZ @@05
|
||
|
||
MOV RAX,RBX
|
||
SHR RBX,16
|
||
ADC RAX,RBX
|
||
POP RBX
|
||
POP RSI
|
||
|
||
@@15: RET
|
||
//************************************
|
||
SYS_HASH_SINGLE_TABLE_FIND1::
|
||
// IN: RAX=HASHED STRING VAL
|
||
// RSI=STR
|
||
// RBX=TYPE MASK
|
||
// RDI=TABLE
|
||
// RCX=INSTANCE, NOT ZERO
|
||
// OUT: RAX=ENTRY OR ZERO NOT FOUND
|
||
// RDX=POINTER TO POINTER TO ENTRY
|
||
// RCX IF NOT FOUND ENOUGH, DECREMENTED BY NUM MATCHES
|
||
// ZERO FLAG SET NOT FOUND
|
||
MOV RCX,1
|
||
SYS_HASH_SINGLE_TABLE_FIND::
|
||
TEST RCX,RCX
|
||
JNZ @@05
|
||
XOR RAX,RAX
|
||
RET
|
||
@@05: AND RAX,U64 CHashTable.mask[RDI]
|
||
MOV RDX,U64 CHashTable.body[RDI]
|
||
LEA RDX,U64 [RDX+RAX*8]
|
||
@@10: MOV RAX,U64 [RDX]
|
||
TEST RAX,RAX
|
||
JNZ @@15
|
||
RET
|
||
|
||
@@15: TEST U32 CHash.type[RAX],EBX
|
||
JZ @@30
|
||
PUSH RAX
|
||
PUSH RDI
|
||
PUSH RSI
|
||
MOV RDI,U64 CHash.str[RAX]
|
||
@@20: LODSB
|
||
CMP U8 [RDI],AL
|
||
JNE @@25
|
||
INC RDI
|
||
TEST AL,AL
|
||
JNZ @@20
|
||
POP RSI
|
||
POP RDI
|
||
POP RAX
|
||
LOOP @@30
|
||
INC U32 CHash.use_cnt[RAX]
|
||
TEST RAX,RAX
|
||
RET
|
||
|
||
@@25: POP RSI
|
||
POP RDI
|
||
POP RAX
|
||
|
||
@@30: LEA RDX,U64 CHash.next[RAX]
|
||
JMP @@10
|
||
//************************************
|
||
SYS_HASH_FIND1::
|
||
// IN: RSI=STR
|
||
// RBX=TYPE MASK
|
||
// RDI=TABLE
|
||
// RCX=INSTANCE NUM
|
||
// OUT: RAX=ENTRY OR ZERO NOT FOUND
|
||
// ZERO FLAG SET NOT FOUND
|
||
MOV RCX,1
|
||
SYS_HASH_FIND::
|
||
PUSH RDI
|
||
CALL SYS_HASH_STR
|
||
|
||
@@05: PUSH RAX
|
||
CALL SYS_HASH_SINGLE_TABLE_FIND
|
||
JNZ @@15
|
||
POP RAX
|
||
@@10: MOV RDI,U64 CHashTable.next[RDI]
|
||
TEST RDI,RDI
|
||
JNZ @@05
|
||
POP RDI
|
||
XOR RAX,RAX
|
||
RET
|
||
|
||
@@15: ADD RSP,8
|
||
POP RDI
|
||
TEST RAX,RAX
|
||
RET
|
||
//************************************
|
||
SYS_HASH_BUCKET_FIND::
|
||
// IN: RSI=STR
|
||
// RDI=TABLE
|
||
// OUT: RAX=BUCKET
|
||
PUSH RDX
|
||
CALL SYS_HASH_STR
|
||
AND RAX,U64 CHashTable.mask[RDI]
|
||
MOV RDX,U64 CHashTable.body[RDI]
|
||
LEA RAX,U64 [RDX+RAX*8]
|
||
POP RDX
|
||
RET
|
||
_HASH_STR::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RSI
|
||
MOV RSI,U64 SF_ARG1[RBP]
|
||
CALL SYS_HASH_STR
|
||
POP RSI
|
||
POP RBP
|
||
RET1 8
|
||
_HASH_FIND::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RSI
|
||
PUSH RDI
|
||
MOV RSI,U64 SF_ARG1[RBP]
|
||
MOV RDI,U64 SF_ARG2[RBP]
|
||
MOV RBX,U64 SF_ARG3[RBP]
|
||
MOV RCX,U64 SF_ARG4[RBP]
|
||
CALL SYS_HASH_FIND
|
||
POP RDI
|
||
POP RSI
|
||
POP RBP
|
||
RET1 32
|
||
_HASH_SINGLE_TABLE_FIND::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RSI
|
||
PUSH RDI
|
||
MOV RSI,U64 SF_ARG1[RBP]
|
||
MOV RDI,U64 SF_ARG2[RBP]
|
||
MOV RBX,U64 SF_ARG3[RBP]
|
||
MOV RCX,U64 SF_ARG4[RBP]
|
||
CALL SYS_HASH_STR
|
||
CALL SYS_HASH_SINGLE_TABLE_FIND
|
||
POP RDI
|
||
POP RSI
|
||
POP RBP
|
||
RET1 32
|
||
_HASH_BUCKET_FIND::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RSI
|
||
PUSH RDI
|
||
MOV RSI,U64 SF_ARG1[RBP]
|
||
MOV RDI,U64 SF_ARG2[RBP]
|
||
CALL SYS_HASH_BUCKET_FIND
|
||
POP RDI
|
||
POP RSI
|
||
POP RBP
|
||
RET1 16
|
||
_HASH_ADD::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RSI
|
||
PUSH RDI
|
||
MOV RCX,U64 SF_ARG1[RBP]
|
||
MOV RSI,U64 CHash.str[RCX]
|
||
MOV RDI,U64 SF_ARG2[RBP]
|
||
CALL SYS_HASH_BUCKET_FIND
|
||
MOV RCX,U64 SF_ARG1[RBP]
|
||
PUSHFD
|
||
CLI
|
||
MOV RBX,U64 [RAX]
|
||
MOV U64 CHash.next[RCX],RBX
|
||
MOV U64 [RAX],RCX
|
||
|
||
POPFD
|
||
POP RDI
|
||
POP RSI
|
||
POP RBP
|
||
RET1 16
|
||
_HASH_ADD_AFTER::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RDI
|
||
MOV RCX,U64 SF_ARG1[RBP]
|
||
MOV RDI,U64 SF_ARG3[RBP]
|
||
PUSHFD
|
||
CLI
|
||
MOV RAX,SF_ARG2[RBP]
|
||
MOV RBX,U64 [RAX]
|
||
MOV U64 CHash.next[RCX],RBX
|
||
MOV U64 [RAX],RCX
|
||
|
||
POPFD
|
||
POP RDI
|
||
POP RBP
|
||
RET1 24
|
||
_HASH_REM_DEL::
|
||
PUSH RBP
|
||
MOV RBP,RSP
|
||
PUSH RSI
|
||
PUSH RDI
|
||
MOV RCX,U64 SF_ARG1[RBP]
|
||
TEST RCX,RCX
|
||
JZ @@10
|
||
MOV RSI,U64 CHash.str[RCX]
|
||
XOR RBX,RBX
|
||
MOV EBX,U32 CHash.type[RCX]
|
||
AND EBX,~HTG_FLAGS_MASK&0xFFFFFFFF
|
||
MOV RDI,U64 SF_ARG2[RBP]
|
||
MOV RCX,U64 SF_ARG3[RBP]
|
||
CALL SYS_HASH_STR
|
||
|
||
PUSHFD
|
||
CLI
|
||
CALL SYS_HASH_SINGLE_TABLE_FIND
|
||
JZ @@05
|
||
CMP RAX,U64 SF_ARG1[RBP]
|
||
JNE @@05
|
||
|
||
MOV RBX,U64 CHash.next[RAX]
|
||
MOV U64 [RDX],RBX
|
||
|
||
POPFD
|
||
|
||
PUSH_C_REGS
|
||
PUSH RAX
|
||
CALL &HashDel
|
||
POP_C_REGS
|
||
|
||
POP RDI
|
||
POP RSI
|
||
MOV RAX,1
|
||
POP RBP
|
||
RET1 24
|
||
|
||
@@05: POPFD
|
||
@@10: POP RDI
|
||
POP RSI
|
||
XOR RAX,RAX
|
||
POP RBP
|
||
RET1 24
|
||
}
|
||
|
||
_extern _HASH_STR I64 HashStr(U8 *st); //Hash a string.
|
||
_extern _HASH_FIND CHash *
|
||
HashFind(U8 *needle_str,CHashTable *haystack_table,I64 mask,I64 instance=1);//Find string in hash table.
|
||
_extern _HASH_SINGLE_TABLE_FIND CHash *
|
||
HashSingleTableFind(U8 *needle_str,CHashTable *haystack_table,I64 mask,I64 instance=1);//Find string in single hash table.
|
||
_extern _HASH_BUCKET_FIND CHash **
|
||
HashBucketFind(U8 *needle_str,CHashTable *haystack_table); //Find hash bucket.
|
||
_extern _HASH_ADD U0 HashAdd(CHash *temph,CHashTable *table); //Add entry to hash table.
|
||
_extern _HASH_REM_DEL Bool HashRemDel(CHash *temph,CHashTable *table,I64 instance=1);//Remove hash entry and del. Instance must match.
|
||
|
||
|