Changeset 41760 in vbox for trunk/src/VBox/Disassembler
- Timestamp:
- Jun 15, 2012 3:56:20 PM (12 years ago)
- Location:
- trunk/src/VBox/Disassembler
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Disassembler/DisasmCore.cpp
r41753 r41760 65 65 static uint32_t disReadDWord(PDISCPUSTATE pCpu, RTUINTPTR pAddress); 66 66 static uint64_t disReadQWord(PDISCPUSTATE pCpu, RTUINTPTR pAddress); 67 static DECLCALLBACK(int) disReadBytesDefault(PDISCPUSTATE p Cpu, uint8_t *pbDst, RTUINTPTR uSrcAddr, uint32_t cbToRead);67 static DECLCALLBACK(int) disReadBytesDefault(PDISCPUSTATE pDis, uint8_t offInstr, uint8_t cbMinRead, uint8_t cbMaxRead); 68 68 69 69 … … 2390 2390 2391 2391 2392 static DECLCALLBACK(int) disReadBytesDefault(PDISCPUSTATE p Cpu, uint8_t *pbDst, RTUINTPTR uSrcAddr, uint32_t cbToRead)2392 static DECLCALLBACK(int) disReadBytesDefault(PDISCPUSTATE pDis, uint8_t offInstr, uint8_t cbMinRead, uint8_t cbMaxRead) 2393 2393 { 2394 2394 #ifdef IN_RING0 2395 2395 AssertMsgFailed(("disReadWord with no read callback in ring 0!!\n")); 2396 RT_BZERO(pbDst, cbToRead); 2396 RT_BZERO(&pDis->abInstr[offInstr], cbMaxRead); 2397 pDis->cbCachedInstr = offInstr + cbMaxRead; 2397 2398 return VERR_DIS_NO_READ_CALLBACK; 2398 2399 #else 2399 memcpy(pbDst, (void const *)(uintptr_t)uSrcAddr, cbToRead); 2400 memcpy(&pDis->abInstr[offInstr], (uint8_t const *)(uintptr_t)pDis->uInstrAddr + offInstr, cbMaxRead); 2401 pDis->cbCachedInstr = offInstr + cbMaxRead; 2400 2402 return VINF_SUCCESS; 2401 2403 #endif … … 2437 2439 2438 2440 /* 2439 * Do the read. No need to zero anything, abInstr is already zeroed by the 2440 * DISInstrEx API. 2441 * Do the read. 2442 * (No need to zero anything on failure as abInstr is already zeroed by the 2443 * DISInstrEx API.) 2441 2444 */ 2442 /** @todo Change the callback API so it can read more, thus avoid lots of 2443 * calls or it doing its own caching. */ 2444 int rc = pCpu->pfnReadBytes(pCpu, &pCpu->abInstr[off], pCpu->uInstrAddr + off, cbMin); 2445 if (RT_FAILURE(rc)) 2445 int rc = pCpu->pfnReadBytes(pCpu, off, cbMin, sizeof(pCpu->abInstr) - off); 2446 if (RT_SUCCESS(rc)) 2447 { 2448 Assert(pCpu->cbCachedInstr >= off + cbMin); 2449 Assert(pCpu->cbCachedInstr <= sizeof(pCpu->abInstr)); 2450 } 2451 else 2446 2452 { 2447 2453 Log(("disReadMore failed with rc=%Rrc!!\n", rc)); 2448 2454 pCpu->rc = VERR_DIS_MEM_READ; 2449 2455 } 2450 pCpu->cbCachedInstr = off + cbMin;2451 2456 } 2452 2457 -
trunk/src/VBox/Disassembler/testcase/tstDisasm-2.cpp
r41737 r41760 167 167 /** 168 168 * Callback for reading bytes. 169 * 170 * @todo This should check that the disassembler doesn't do unnecessary reads, 171 * however the current doesn't do this and is just complicated... 172 */ 173 static DECLCALLBACK(int) MyDisasInstrRead(PDISCPUSTATE pDisState, uint8_t *pbDst, RTUINTPTR uSrcAddr, uint32_t cbToRead) 174 { 175 PMYDISSTATE pState = (PMYDISSTATE)pDisState; 169 */ 170 static DECLCALLBACK(int) MyDisasInstrRead(PDISCPUSTATE pDis, uint8_t offInstr, uint8_t cbMinRead, uint8_t cbMaxRead) 171 { 172 PMYDISSTATE pState = (PMYDISSTATE)pDis; 173 RTUINTPTR uSrcAddr = pState->Cpu.uInstrAddr + offInstr; 176 174 if (RT_LIKELY( pState->uNextAddr == uSrcAddr 177 && pState->cbLeft >= cb ToRead))175 && pState->cbLeft >= cbMinRead)) 178 176 { 179 177 /* 180 178 * Straight forward reading. 181 179 */ 182 if (cbToRead == 1) 180 //size_t cbToRead = cbMaxRead; 181 size_t cbToRead = cbMinRead; 182 memcpy(&pState->Cpu.abInstr[offInstr], pState->pbNext, cbToRead); 183 pState->Cpu.cbCachedInstr = offInstr + cbToRead; 184 pState->pbNext += cbToRead; 185 pState->cbLeft -= cbToRead; 186 pState->uNextAddr += cbToRead; 187 return VINF_SUCCESS; 188 } 189 190 if (pState->uNextAddr == uSrcAddr) 191 { 192 /* 193 * Reading too much. 194 */ 195 if (pState->cbLeft > 0) 183 196 { 184 pState->cbLeft--; 185 *pbDst = *pState->pbNext++; 186 pState->uNextAddr++; 197 memcpy(&pState->Cpu.abInstr[offInstr], pState->pbNext, pState->cbLeft); 198 offInstr += (uint8_t)pState->cbLeft; 199 cbMinRead -= (uint8_t)pState->cbLeft; 200 pState->pbNext += pState->cbLeft; 201 pState->uNextAddr += pState->cbLeft; 202 pState->cbLeft = 0; 187 203 } 188 else 189 { 190 memcpy(pbDst, pState->pbNext, cbToRead); 191 pState->pbNext += cbToRead; 192 pState->cbLeft -= cbToRead; 193 pState->uNextAddr += cbToRead; 194 } 204 memset(&pState->Cpu.abInstr[offInstr], 0xcc, cbMinRead); 205 pState->rc = VERR_EOF; 195 206 } 196 207 else 197 208 { 198 209 /* 199 * Jumping up the stream. 200 * This occurs when the byte sequence is added to the output string. 210 * Non-sequential read, that's an error. 201 211 */ 202 uint64_t offReq64 = uSrcAddr - pState->uAddress; 203 if (offReq64 < 32) 204 { 205 uint32_t offReq = offReq64; 206 uintptr_t off = pState->pbNext - pState->pbInstr; 207 if (off + pState->cbLeft <= offReq) 208 { 209 pState->pbNext += pState->cbLeft; 210 pState->uNextAddr += pState->cbLeft; 211 pState->cbLeft = 0; 212 213 memset(pbDst, 0xcc, cbToRead); 214 pState->rc = VERR_EOF; 215 return VERR_EOF; 216 } 217 218 /* reset the stream. */ 219 pState->cbLeft += off; 220 pState->pbNext = pState->pbInstr; 221 pState->uNextAddr = pState->uAddress; 222 223 /* skip ahead. */ 224 pState->cbLeft -= offReq; 225 pState->pbNext += offReq; 226 pState->uNextAddr += offReq; 227 228 /* do the reading. */ 229 if (pState->cbLeft >= cbToRead) 230 { 231 memcpy(pbDst, pState->pbNext, cbToRead); 232 pState->cbLeft -= cbToRead; 233 pState->pbNext += cbToRead; 234 pState->uNextAddr += cbToRead; 235 } 236 else 237 { 238 if (pState->cbLeft > 0) 239 { 240 memcpy(pbDst, pState->pbNext, pState->cbLeft); 241 pbDst += pState->cbLeft; 242 cbToRead -= (uint32_t)pState->cbLeft; 243 pState->pbNext += pState->cbLeft; 244 pState->uNextAddr += pState->cbLeft; 245 pState->cbLeft = 0; 246 } 247 memset(pbDst, 0xcc, cbToRead); 248 pState->rc = VERR_EOF; 249 return VERR_EOF; 250 } 251 } 252 else 253 { 254 RTStrmPrintf(g_pStdErr, "Reading before current instruction!\n"); 255 memset(pbDst, 0x90, cbToRead); 256 pState->rc = VERR_INTERNAL_ERROR; 257 return VERR_INTERNAL_ERROR; 258 } 259 } 260 261 return VINF_SUCCESS; 212 RTStrmPrintf(g_pStdErr, "Reading before current instruction!\n"); 213 memset(&pState->Cpu.abInstr[offInstr], 0x90, cbMinRead); 214 pState->rc = VERR_INTERNAL_ERROR; 215 } 216 pState->Cpu.cbCachedInstr = offInstr + cbMinRead; 217 return pState->rc; 262 218 } 263 219 … … 340 296 || State.Cpu.pCurInstr->uOpcode == OP_INVALID 341 297 || State.Cpu.pCurInstr->uOpcode == OP_ILLUD2 342 || ( 298 || ( State.enmUndefOp == kUndefOp_DefineByte 343 299 && !MyDisasIsValidInstruction(&State.Cpu)); 344 300 if (State.fUndefOp && State.enmUndefOp == kUndefOp_DefineByte) … … 347 303 { 348 304 State.Cpu.abInstr[0] = 0; 349 State.Cpu.pfnReadBytes(&State.Cpu, &State.Cpu.abInstr[0], State.uAddress, 1);305 State.Cpu.pfnReadBytes(&State.Cpu, 0, 1, 1); 350 306 State.cbInstr = 1; 351 307 }
Note:
See TracChangeset
for help on using the changeset viewer.