i have no idea why its working but this is the code:
Code: Select all
#define HD_PORT_DATA 0x1f0
#define HD_PORT_ERROR 0x1f1
#define HD_PORT_SECT_COUNT 0x1f2
#define HD_PORT_SECT_NUM 0x1f3
#define HD_PORT_CYL_LOW 0x1f4
#define HD_PORT_CYL_HIGH 0x1f5
#define HD_PORT_DRV_HEAD 0x1f6
#define HD_PORT_STATUS 0x1f7
#define HD_PORT_COMMAND 0x1f7
#define HD_READ 0x20
#define HD_WRITE 0x30
#define inb(port) (__extension__({ \
unsigned char __res; \
__asm__ ("inb %%dx, %%al\n\t" \
:"=a"(__res) \
:"dx"(port)); \
__res; \
}))
#define outb(value, port) __asm__ ( \
"outb %%al, %%dx\n\t"::"al"(value), "dx"(port))
#define insl(port, buf, nr) \
__asm__ ("cld;rep;insl\n\t" \
::"d"(port), "D"(buf), "c"(nr))
#define outsl(buf, nr, port) \
__asm__ ("cld;rep;outsl\n\t" \
::"d"(port), "S" (buf), "c" (nr))
void Read(unsigned int lba, unsigned int sects_to_access, void *buf)
{
/* lba to chs */
/* cylinder = LBA / (heads_per_cylinder * sectors_per_track)
temp = LBA % (heads_per_cylinder * sectors_per_track)
head = temp / sectors_per_track
sector = temp % sectors_per_track + 1 */
unsigned int cyl = lba/(HD0.head * HD0.sect);
unsigned int head = (lba%(HD0.head*HD0.sect))/HD0.sect;
unsigned int sect = (lba%(HD0.head*HD0.sect))%HD0.sect+1;
while ((inb(HD_PORT_STATUS)&0xc0)!=0x40)
;
outb(sects_to_access, HD_PORT_SECT_COUNT);
outb(sect, HD_PORT_SECT_NUM);
outb(cyl, HD_PORT_CYL_LOW);
outb(cyl>>8, HD_PORT_CYL_HIGH);
outb(0xa0|head, HD_PORT_DRV_HEAD);
outb(HD_READ, HD_PORT_COMMAND);
while (! (inb(HD_PORT_STATUS)&0x8))
;
insl(HD_PORT_DATA, buf, sects_to_access<<7);
}
void Write(unsigned int lba, unsigned int sects_to_access, void *buf)
{
/* lba to chs */
/* cylinder = LBA / (heads_per_cylinder * sectors_per_track)
temp = LBA % (heads_per_cylinder * sectors_per_track)
head = temp / sectors_per_track
sector = temp % sectors_per_track + 1 */
unsigned int cyl = lba/(HD0.head * HD0.sect);
unsigned int head = (lba%(HD0.head*HD0.sect))/HD0.sect;
unsigned int sect = (lba%(HD0.head*HD0.sect))%HD0.sect+1;
while ((inb(HD_PORT_STATUS)&0xc0)!=0x40)
;
outb(sects_to_access, HD_PORT_SECT_COUNT);
outb(sect, HD_PORT_SECT_NUM);
outb(cyl, HD_PORT_CYL_LOW);
outb(cyl>>8, HD_PORT_CYL_HIGH);
outb(0xa0|head, HD_PORT_DRV_HEAD);
outb(HD_WRITE, HD_PORT_COMMAND);
while (! (inb(HD_PORT_STATUS)&0x8))
;
outsl(buf, sects_to_access<<7, HD_PORT_DATA);
}
Code: Select all
char buffer[512];
memset(buffer, 'a', 512);
buffer[511] = '\0';
Video_PutString("Empty buffer:");
Video_PutString(buffer);
Video_PutString("\n");
HardDrive::Write(45, 1, buffer);
memset(buffer, 'b', 512);
buffer[511] = '\0';
HardDrive::Read(45, 1, buffer);
buffer[511] = '\0';
Video_PutString("Sector buffer:");
Video_PutString(buffer);
Video_PutString("\n");
Empty buffer:
aaaa....
Sector buffer:
so something is happening to the buffer in HardDrive::Read as it should be full of b's.
Any ways, im not sure where the problem lies.