March 30th, 2012, 4:47
void software_reset(WORD portCtrl)
{
__asm
{
xor eax, eax
xor edx, edx
mov dx, word ptr[portCtrl]
mov al, _CONTROL_SRST_
out dx, al
}
}
void watch_dog(DWORD* pCount)
{
(*pCount)++;
if((*pCount) >= 0x100000)
{
__asm int 3
(*pCount) = 0;
}
}
void wait_until_ready(WORD portBase)
{
DWORD count = 0;
__asm
{
L_READ:
lea eax, dword ptr[count]
push eax
call watch_dog
mov dx, word ptr[portBase]
xor eax, eax
add dx, 0x7 //status
in al, dx
test al, (_STATUS_BSY_ | _STATUS_DRQ_)
jz L_RET
nop
nop
nop
jmp L_READ
}
L_RET:
__asm int 3
return;
}
void DriverEntry()
{
software_reset(0x3F6);
wait_until_ready(0x1F0);
}March 30th, 2012, 6:02
March 30th, 2012, 21:37
guru wrote:Hi, Don't have time but take look here
http://www.serialata.org/documents/SATA ... rs_000.pdf
March 30th, 2012, 22:53
part of explantion wrote:summary:
Resetting a drive / Software Reset
For non-ATAPI drives, the only method a driver has of resetting a drive after a major error is to do a "software reset" on the bus. Set bit 2 (SRST, value = 4) in the proper Control Register for the bus. This will reset both ATA devices on the bus. Then, you have to clear that bit again, yourself. The master drive on the bus is automatically selected. ATAPI drives set values on their LBA_LOW and LBA_HIGH IO ports, but are not supposed to reset or even terminate their current command.
March 30th, 2012, 23:34
Powered by phpBB © phpBB Group.