📄 ide_drv.h
字号:
} HIMAWARI_FORMAT_DESCRIPTOR;
typedef struct atapi_mode_sense_packet_desc
{
byte op_code;
byte lun;
byte pc_code_page;
byte reserved1;
byte reserved2;
byte reserved3;
byte reserved4;
TRANSFER_LENGTH transfer_length; /*Big Endian format*/
byte reserved5;
byte reserved6;
byte reserved7;
} ATAPI_MODE_SENSE_PACKET_DESC;
typedef struct atapi_format_unit_packet_desc
{
byte op_code;
byte defect_list_format;
byte track_number;
byte interleave[2];
byte reserved[7];
} ATAPI_FORMAT_UNIT_PACKET_DESC;
typedef struct atapi_start_stop_packet_desc
{
byte op_code;
byte lun;
byte reserved1;
byte reserved2;
byte eject; /* Bit 1 is eject, 0 is start */
byte reserved[7];
} ATAPI_START_STOP_UNIT_PACKET_DESC;
typedef struct atapi_old_format_unit_packet_desc
{
byte op_code;
byte reserved1;
byte medium;
byte reserved2[3];
byte control_byte;
byte track_number;
byte reserved3[4];
} ATAPI_OLD_FORMAT_UNIT_PACKET_DESC;
typedef struct atapi_packet_desc
{
byte op_code;
byte lun;
dword lba;
byte reserved1;
TRANSFER_LENGTH transfer_length; /*Big Endian format*/
byte reserved2;
byte reserved3;
byte reserved4;
} ATAPI_PACKET_DESC;
typedef union {
ATAPI_PACKET_DESC generic;
ATAPI_MODE_SENSE_PACKET_DESC mode_sense;
ATAPI_FORMAT_UNIT_PACKET_DESC format;
ATAPI_OLD_FORMAT_UNIT_PACKET_DESC old_format;
ATAPI_START_STOP_UNIT_PACKET_DESC start_stop;
} ATAPI_PACKET;
/* ide_control structure - We use this abstraction to manage the IDE
driver.
Structure contents:
. drive description. logical drive structure (heads/secptrak/secpcyl)
. virtual registers: These aren't (can't be) mapped onto the
the controller but we use virtual representation on the
register file to drive the system.
. virtual output register file (to drive) - We load the registers
and then ask lower level code to send the command block to the
controller.
. virtual input register file (from drive) - We offload the register
file from the drive into these fields after a command complete.
Note: We only offload the whole register file in certain cases.
The status register is always offloaded.
*/
/* The control structure contains one of these per drive [2]. We set this
up at init time after issueing SET_PARAMS. The values are used to convert
block number to track:head:sector */
typedef struct ide_drive_desc
{
word open_count; /*CDROM Support Jerry */
byte num_heads;
byte sec_p_track;
word sec_p_cyl;
word num_cylinders;
byte max_multiple;
BOOLEAN supports_lba;
dword total_lba;
byte protocol;
ATAPI_PACKET atapi_packet;
word atapi_packet_size;
byte media_descriptor;
byte medium_type_code;
byte allocation_unit;
byte CMD_DRQ_type; /*CDROM Alan */
} IDE_DRIVE_DESC;
typedef struct ide_control
{
IOADDRESS register_file_address; /* Address of the controller */
int interrupt_number; /* -1 if not being used */
int controller_number;
BOOLEAN command_complete; /* Set by ISR when operation is complete */
word error_code; /* Set if an error occured - This is the error
reported to the user */
word timer; /* Command fails if this much time elapsed */
byte block_size; /* Block size for read/write multiple cmds */
word sectors_remaining; /* Sectors remaining for read/write mult */
PFBYTE user_address; /* C pointer address of the user's buffer */
/* Geometry of the drives */
IDE_DRIVE_DESC drive[2];
/* Virtual output register file - we load these and then send them to
the IDE drive. */
byte vo_write_precomp; /* Used to turn on read ahead on certain drives */
byte vo_sector_count; /* Sector transfer request */
byte vo_sector_number; /* Sector number request */
byte vo_cyl_low; /* Low byte of cylinder */
byte vo_cyl_high; /* High byte of cylinder */
byte vo_drive_head; /* Drive & Head register
Bit 5 == 1
Bit 4 = Drive 0/1 == C/D,
bit 0-3 == head */
byte vo_feature; /* Feature register */
byte vo_command; /* command register see command patterns above (W) */
byte vo_dig_out; /* Digital output register. Bits enable interrupts
and software reset See BIT patterns above */
/* Virtual input register file - We read these from the drive during our
command completion code */
byte vi_error; /* Error register. See IDE_ERB_XXXX above */
byte vi_sector_count; /* # Sectors left in request */
byte vi_sector_number; /* Current sector number in request */
byte vi_cyl_low; /* Low byte of cylinder in request */
byte vi_cyl_high; /* High byte of cylinder in request */
byte vi_drive_head; /* Drive & Head register in request */
/* Byte 5 == 1
Byte 4 = Drive 1/0 == C/D,
bytes 0-3 == head */
byte vi_status; /* Status register see IDE_STB_XXXX above. Reading
this register sends an interrupt acknowledge
to the drive. */
byte vi_alt_status; /* Same as status register but does not clear
interrupt state. */
byte vi_drive_addr; /* Bit 0 & 1 are a mask of which drive is selected
bits 2-5 are the head number in ones complement.
~(BITS2-5) == head number */
} IDE_CONTROLLER;
typedef IDE_CONTROLLER * PIDE_CONTROLLER;
#define ide_inbyte(X) ((byte) INBYTE((IOADDRESS) (X) ))
#define ide_outbyte(X,Y) OUTBYTE((IOADDRESS) (X), (byte)(Y))
#define ide_rd_status(X) ide_inbyte((X)->register_file_address + IDE_OFF_STATUS)
#define ide_rd_sector_count(X) ide_inbyte((X)->register_file_address + IDE_OFF_SECTOR_COUNT)
#define ide_rd_alt_status(X) ide_inbyte((X)->register_file_address + IDE_OFF_ALT_STATUS)
#define ide_rd_error(X) ide_inbyte((X)->register_file_address + IDE_OFF_ERROR)
#define ide_rd_sector_number(X) ide_inbyte((X)->register_file_address + IDE_OFF_SECTOR_NUMBER)
#define ide_rd_cyl_low(X) ide_inbyte((X)->register_file_address + IDE_OFF_CYL_LOW)
#define ide_rd_cyl_high(X) ide_inbyte((X)->register_file_address + IDE_OFF_CYL_HIGH)
#define ide_rd_drive_head(X) ide_inbyte((X)->register_file_address + IDE_OFF_DRIVE_HEAD)
#define ide_rd_drive_address(X) ide_inbyte((X)->register_file_address + IDE_OFF_DRIVE_ADDRESS)
#define ide_wr_dig_out(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_DIG_OUTPUT, Y)
#define ide_wr_sector_count(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_SECTOR_COUNT, Y)
#define ide_wr_sector_number(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_SECTOR_NUMBER, Y)
#define ide_wr_cyl_low(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_CYL_LOW, Y)
#define ide_wr_cyl_high(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_CYL_HIGH, Y)
#define ide_wr_drive_head(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_DRIVE_HEAD, Y)
#define ide_wr_command(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_COMMAND, Y)
#define ide_wr_feature(X, Y) ide_outbyte((X)->register_file_address + IDE_OFF_FEATURE, Y)
/* Function prototypes */
BOOLEAN ide_io(int driveno, dword sector, void *buffer, word count, BOOLEAN reading);
int ide_perform_device_ioctl(int driveno, int opcode, PFVOID pargs);
void ide_interrupt(int controller_no);
BOOLEAN ide_command_identify(PIDE_CONTROLLER pc, PFBYTE address, int phys_drive);
void ide_interrupt(int controller_no);
BOOLEAN ide_wait_ready(PIDE_CONTROLLER pc,int ticks);
BOOLEAN ide_wait_not_busy(PIDE_CONTROLLER pc,int ticks);
BOOLEAN ide_wait_drq(PIDE_CONTROLLER pc, int ticks);
#endif /* #if (USE_ATA) */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -