Rev 4272 | Rev 4294 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 4272 | Rev 4289 | ||
---|---|---|---|
Line 6... | Line 6... | ||
6 | ;; 20/11/2013 yogev_ezra: Initial version ;; |
6 | ;; 20/11/2013 yogev_ezra: Initial version ;; |
7 | ;; Thanks for help to: dunkaist, eAndrew, hidnplayr, Mario ;; |
7 | ;; Thanks for help to: dunkaist, eAndrew, hidnplayr, Mario ;; |
8 | ;; ;; |
8 | ;; ;; |
9 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
9 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
Line 10... | Line 10... | ||
10 | 10 | ||
Line 11... | Line 11... | ||
11 | $Revision: 4272 $ |
11 | $Revision: 4289 $ |
12 | 12 | ||
Line 13... | Line 13... | ||
13 | VORTEX86DEBUG = 0 ; For testing in emulators and in non-Vortex86 CPU computers, set this to 1 |
13 | VORTEX86DEBUG = 0 ; For testing in emulators and in non-Vortex86 CPU computers, set this to 1 |
Line 42... | Line 42... | ||
42 | cmp [cpu_vendor], 'Vort' |
42 | cmp [cpu_vendor], 'Vort' |
43 | jnz .Vortex86end ; If the CPU vendor is not 'Vortex86 SoC', skip the SoC detection |
43 | jnz .Vortex86end ; If the CPU vendor is not 'Vortex86 SoC', skip the SoC detection |
44 | end if |
44 | end if |
Line 45... | Line 45... | ||
45 | 45 | ||
46 | mov dx, 0xcf8 ; CF8h = Vortex86 PCI Configuration Address port |
46 | mov dx, 0xcf8 ; CF8h = Vortex86 PCI Configuration Address port |
47 | mov eax, 0x80000090 ; 0x80000090 = Starting PCI address to read from (32-bit register - accessed as DWORD) |
47 | mov eax, OS_BASE+0x90 ; 0x80000090 = Starting PCI address to read from (32-bit register - accessed as DWORD) |
48 | out dx, eax ; Send request to PCI address port to retrieve data from this address |
48 | out dx, eax ; Send request to PCI address port to retrieve data from this address |
49 | mov dx, 0xcfc ; CFCh = Vortex86 PCI Configuration Data port |
49 | mov dx, 0xcfc ; CFCh = Vortex86 PCI Configuration Data port |
Line 50... | Line 50... | ||
50 | in eax, dx ; Read data (SoC type) from PCI data port |
50 | in eax, dx ; Read data (SoC type) from PCI data port |
51 | 51 | ||
52 | if VORTEX86DEBUG ; When in debug mode, pretend that we received port output equal to "VORTEX86DEBUGVALUE" |
52 | if VORTEX86DEBUG ; When in debug mode, pretend that we received port output equal to "VORTEX86DEBUGVALUE" |
Line 53... | Line 53... | ||
53 | mov eax, VORTEX86DEBUGVALUE |
53 | mov eax, VORTEX86DEBUGVALUE |
54 | end if |
54 | end if |
55 | 55 | ||
56 | DEBUGF 1, "K : Vortex86 SoC register returned 0x" |
56 | DEBUGF 1, "K : Vortex86 SoC register returned 0x" |
57 | test eax, eax ; We need to break out in case the result is '\0' since otherwise we will fail at NULL string |
57 | test eax, eax ; Check whether the port output was '\0' |
- | 58 | jz .nullPCIoutput ; In case the result is '\0' (NULL), skip further testing and exit |
|
58 | jz .nullPCIoutput |
59 | mov [Vortex86CPUcode], eax ; Save HEX CPU code to Vortex86CPUcode (so it can be used later) |
59 | mov [Vortex86CPUcode], eax |
- | |
60 | DEBUGF 1, "%x (%s): ", eax, Vortex86CPUcode |
60 | DEBUGF 1, "%x (%s): ", eax, Vortex86CPUcode ; Print the CPU code (as HEX and as string) to debug log |
61 | cmp ax, 4d44h ; Check whether it's Vortex86 family (all Vortex86 SoC have ID in form of "0xNN504d44") |
61 | |
62 | jnz .notVortex86 |
62 | mov ebx, 0x444d5000 ; Apply Vortex86 CPU code mask (all Vortex86 SoC have ID in form of "0xNN504d44") |
63 | shr eax, 16 ; Discard lower word in EAX which is always 4d44h in Vortex86 family |
63 | bswap eax ; Assumed it is Vortex86 SoC, the highest byte identifies the exact CPU, so move it to the lowest byte |
- | 64 | mov bl, al ; Copy SoC type to BL since EAX (that includes AL) is used implicitly in "LODSD" command below |
|
64 | cmp al, 50h ; The 3rd byte is always 50h in Vortex86 SoC (if this is the case, we need just the highest byte) |
65 | cmp eax, ebx ; Now see whether the 3 higher bytes were "0x504d44" (which means it's Vortex86) |
65 | jnz .notVortex86 |
66 | jnz .notVortex86 ; Sorry, it's not Vortex86 - go say so and exit |
66 | mov bl, ah ; Copy SoC type to BL since EAX (that includes AH) is used implicitly in "LODSD" command below |
67 | |
67 | mov esi, Vortex86SoClist ; ESI points to the start of Vortex86SoClist (used implicitly in "LODSD" command below) |
68 | mov esi, Vortex86SoClist ; ESI points to the start of Vortex86SoClist (used implicitly in "LODSD" command below) |
- | 69 | xor ecx, ecx ; Zero ECX (it is used as counter) |
|
68 | xor ecx, ecx ; Zero ECX (it is used as counter) |
70 | cld ; Clears the DF flag in the EFLAGS register (DF=0 --> String operations increment ESI) |
69 | cld ; Clears the DF flag in the EFLAGS register (DF=0 --> String operations increment ESI) |
71 | @@: |
70 | @@: |
- | |
71 | cmp ecx, Vortex86SoCnum ; Check if we iterated Vortex86SoCnum times already (i.e. went over the entire Vortex86SoClist) |
72 | inc ecx ; Increment our counter |
72 | ja .unknownVortex86 ; If the entire list was tested and our CPU is not in that list, it is unknown Vortex86 SoC |
73 | cmp ecx, Vortex86SoCnum ; Check if we iterated Vortex86SoCnum times already (i.e. went over the entire Vortex86SoClist) |
73 | inc ecx ; Increment our counter |
74 | ja .unknownVortex86 ; If the entire list was tested and our CPU is not in that list, it is unknown Vortex86 SoC |
Line 74... | Line 75... | ||
74 | lodsd ; Load DWORD at address DS:ESI into EAX (puts 1 line from Vortex86SoClist into EAX, then increments ESI) |
75 | lodsd ; Load DWORD at address DS:ESI into EAX (puts 1 line from Vortex86SoClist into EAX, then increments ESI) |
75 | cmp bl, al ; Check if our CPU matches the current record in the list |
76 | cmp bl, al ; Check if our CPU matches the current record in the list |
76 | jne @b ; No match --> repeat with next record |
77 | jne @b ; No match --> repeat with next record |
- | 78 | ||
- | 79 | shr eax, 8 ; Match found --> drop the SoC type code from Vortex86SoClist name and replace it with \0 |
|
Line 77... | Line -... | ||
77 | - | ||
78 | shr eax, 8 ; Match found --> drop the SoC type code from Vortex86SoClist name and replace it with \0 |
- | |
79 | mov dword [Vortex86SoCname+8], eax ; Concatenate it with prefix to receive complete SoC name (\0 is string termination) |
- | |
80 | mov [Vortex86CPUid], cl ; Save the CPUid (1=Vortex86SX, 2=Vortex86DX, ..., Vortex86SoCnum+1=Unknown Vortex86) |
80 | mov dword [Vortex86SoCname+8], eax ; Concatenate it with prefix to receive complete SoC name (\0 is string termination) |
81 | 81 | mov [Vortex86CPUid], cl ; Save the CPUid (1=Vortex86SX, 2=Vortex86DX, ..., Vortex86SoCnum+1=Unknown Vortex86) |
|
82 | DEBUGF 1, "%s (id=%d)\n", Vortex86SoCname, [Vortex86CPUid]:1 |
82 | DEBUGF 1, "%s (id=%d)\n", Vortex86SoCname, [Vortex86CPUid]:1 ; Say what we have found (CPU name and id) |
Line 83... | Line 83... | ||
83 | jmp .Vortex86end ; Say what we have found (CPU name and id) and exit |
83 | jmp .Vortex86end |
84 | 84 | ||
85 | .nullPCIoutput: ; Emulators and non-Vortex86 CPU computers will usually return \0 in this register |
85 | .notVortex86: ; In case this register is used by other CPUs for other purpose, it's interesting what it contains |
86 | DEBUGF 1, "0 (NULL)\n" |
86 | DEBUGF 1, "not a Vortex86 CPU\n" |
Line 87... | Line 87... | ||
87 | jmp .Vortex86end |
87 | jmp .Vortex86end |
88 | 88 | ||
Line 89... | Line 89... | ||
89 | .unknownVortex86: |
89 | .unknownVortex86: |
90 | mov [Vortex86CPUid], cl ; Save the CPUid (Vortex86SoCnum+1=Unknown Vortex86) |
90 | mov [Vortex86CPUid], cl ; Save the CPUid (Vortex86SoCnum+1=Unknown Vortex86) |