sector madness

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
drnono
Posts: 23
Joined: Sun Aug 09, 2015 11:54 am

sector madness

Post by drnono »

I'm having a problem trying to read ATA with 28bit LBA. It's weird. Some things work, some things don't.

For example: If I read 250 sectors starting at LBA 1, I can read the sector at sector 202 as expected. If I read sectors starting at sector 200 sector 202 shows up all zeros.

I did a test and filled a sector at 222 which I can't read from sector 190, but I can read sector 202 from there. I can read sector 222 from sector 200.

Code: Select all

	
uint16_t *disk_buffer = (uint16_t *) 0x100000;

uint32_t LBA = 64+200;
	uint16_t numSectors = 250;
	ATA_read(&ide_disks[1], disk_buffer, LBA, numSectors);


		LBA_0 =  LBA & 0x000000ff;		// 3.5 bytes
		LBA_1 = (LBA & 0x0000ff00) >> 8;
		LBA_2 = (LBA & 0x00ff0000) >> 16;
		LBA_3 = (LBA & 0x0f000000) >> 24;

		//outb( disk->IO_base_address + ATA_DRIVESEL_REGISTER, (disk->slave_bit << 4) | LBA_3 | 0b11100000);  // bit 7, bit6=lba bit, bit6             these bits don't seem to work on bochs or vmware
		outb( disk->IO_base_address + ATA_DRIVESEL_REGISTER, (disk->slave_bit << 4) | LBA_3 );  
		outb( disk->IO_base_address + ATA_SECTOR_COUNT_REGISTER, sectors_count );
		outb( disk->IO_base_address + ATA_LBA_LO_REGISTER, LBA_0 );
		outb( disk->IO_base_address + ATA_LBA_MID_REGISTER, LBA_1 );
		outb( disk->IO_base_address + ATA_LBA_HI_REGISTER, LBA_2 );

		outb( disk->IO_base_address + ATA_COMMAND_REGISTER, ATA_READ_PIO );

	for (uint8_t i=0; i<sectors_count; i++)
	{
	//poll
		while (1)
		{
			poll_status = inb( disk->control_base_address + ATA_ALT_STATUS_REGISTER );
			if ( !(poll_status & ATA_BSY) && (poll_status & ATA_DRQ) ) break;
		}
	// read a sector at a time (256 words = 512)	
		for (uint16_t j=0; j<256; j++)
		{
			disk_buffer[index] = inw( disk->IO_base_address + ATA_DATA_REGISTER );
			index++;
		}
	}
Octocontrabass
Member
Member
Posts: 5568
Joined: Mon Mar 25, 2013 7:01 pm

Re: sector madness

Post by Octocontrabass »

drnono wrote:

Code: Select all

		//outb( disk->IO_base_address + ATA_DRIVESEL_REGISTER, (disk->slave_bit << 4) | LBA_3 | 0b11100000);  // bit 7, bit6=lba bit, bit6             these bits don't seem to work on bochs or vmware
		outb( disk->IO_base_address + ATA_DRIVESEL_REGISTER, (disk->slave_bit << 4) | LBA_3 );
If you don't set bit 6 when you write to this register, you're not using LBA.
Post Reply