From bdd467547a18194c04b199d736209f67c7c53aa8 Mon Sep 17 00:00:00 2001 From: Natalia Portillo Date: Thu, 29 Jul 2021 00:46:47 +0100 Subject: [PATCH] Fix 48-bit ATA commands. --- aaruremote.h | 18 ++++--- freebsd/ata.c | 12 ++--- linux/ata.c | 27 +++++----- worker.c | 138 ++++++++++++++++++++++++-------------------------- 4 files changed, 100 insertions(+), 95 deletions(-) diff --git a/aaruremote.h b/aaruremote.h index 306daa2..c3fdada 100644 --- a/aaruremote.h +++ b/aaruremote.h @@ -321,9 +321,12 @@ typedef struct { uint16_t feature; uint16_t sector_count; - uint16_t lba_low; - uint16_t lba_mid; - uint16_t lba_high; + uint8_t lba_low_prev; + uint8_t lba_low_cur; + uint8_t lba_mid_prev; + uint8_t lba_mid_cur; + uint8_t lba_high_prev; + uint8_t lba_high_cur; uint8_t device_head; uint8_t command; } AtaRegistersLba48; @@ -333,9 +336,12 @@ typedef struct uint8_t status; uint8_t error; uint16_t sector_count; - uint16_t lba_low; - uint16_t lba_mid; - uint16_t lba_high; + uint8_t lba_low_prev; + uint8_t lba_low_cur; + uint8_t lba_mid_prev; + uint8_t lba_mid_cur; + uint8_t lba_high_prev; + uint8_t lba_high_cur; uint8_t device_head; } AtaErrorRegistersLba48; diff --git a/freebsd/ata.c b/freebsd/ata.c index 1bcddc9..fbe02f4 100644 --- a/freebsd/ata.c +++ b/freebsd/ata.c @@ -296,12 +296,12 @@ int32_t SendAtaLba48Command(void* device_ctx, camccb->ataio.cmd.command = registers.command; camccb->ataio.cmd.device = 0x40 | registers.device_head; - camccb->ataio.cmd.lba_high_exp = (registers.lba_high & 0xFF00) >> 8; - camccb->ataio.cmd.lba_high = registers.lba_high & 0xFF; - camccb->ataio.cmd.lba_mid_exp = (registers.lba_mid & 0xFF00) >> 8; - camccb->ataio.cmd.lba_mid = registers.lba_mid & 0xFF; - camccb->ataio.cmd.lba_low_exp = (registers.lba_low & 0xFF00) >> 8; - camccb->ataio.cmd.lba_low = registers.lba_low & 0xFF; + camccb->ataio.cmd.lba_high_exp = registers.lba_high_cur; + camccb->ataio.cmd.lba_high = registers.lba_high_prev; + camccb->ataio.cmd.lba_mid_exp = registers.lba_mid_cur; + camccb->ataio.cmd.lba_mid = registers.lba_mid_prev; + camccb->ataio.cmd.lba_low_exp = registers.lba_low_cur; + camccb->ataio.cmd.lba_low = registers.lba_low_prev; camccb->ataio.cmd.features_exp = (registers.feature & 0xFF00) >> 8; camccb->ataio.cmd.features = registers.feature & 0xFF; camccb->ataio.cmd.sector_count_exp = (registers.sector_count & 0xFF00) >> 8; diff --git a/linux/ata.c b/linux/ata.c index 20db1b6..f0b733f 100644 --- a/linux/ata.c +++ b/linux/ata.c @@ -236,12 +236,12 @@ int32_t SendAtaLba48Command(void* device_ctx, cdb[4] = (registers.feature & 0xFF); cdb[5] = ((registers.sector_count & 0xFF00) >> 8); cdb[6] = (registers.sector_count & 0xFF); - cdb[7] = ((registers.lba_low & 0xFF00) >> 8); - cdb[8] = (registers.lba_low & 0xFF); - cdb[9] = ((registers.lba_mid & 0xFF00) >> 8); - cdb[10] = (registers.lba_mid & 0xFF); - cdb[11] = ((registers.lba_high & 0xFF00) >> 8); - cdb[12] = (registers.lba_high & 0xFF); + cdb[7] = registers.lba_low_prev; + cdb[8] = registers.lba_low_cur; + cdb[9] = registers.lba_mid_prev; + cdb[10] = registers.lba_mid_cur; + cdb[11] = registers.lba_high_prev; + cdb[12] = registers.lba_high_cur; cdb[13] = registers.device_head; cdb[14] = registers.command; @@ -261,12 +261,15 @@ int32_t SendAtaLba48Command(void* device_ctx, error_registers->error = sense_buf[11]; - error_registers->sector_count = (uint16_t)((sense_buf[12] << 8) + sense_buf[13]); - error_registers->lba_low = (uint16_t)((sense_buf[14] << 8) + sense_buf[15]); - error_registers->lba_mid = (uint16_t)((sense_buf[16] << 8) + sense_buf[17]); - error_registers->lba_high = (uint16_t)((sense_buf[18] << 8) + sense_buf[19]); - error_registers->device_head = sense_buf[20]; - error_registers->status = sense_buf[21]; + error_registers->sector_count = (uint16_t)((sense_buf[12] << 8) + sense_buf[13]); + error_registers->lba_low_prev = sense_buf[14]; + error_registers->lba_low_cur = sense_buf[15]; + error_registers->lba_mid_prev = sense_buf[16]; + error_registers->lba_mid_cur = sense_buf[17]; + error_registers->lba_high_prev = sense_buf[18]; + error_registers->lba_high_cur = sense_buf[19]; + error_registers->device_head = sense_buf[20]; + error_registers->status = sense_buf[21]; *sense = error_registers->error != 0 || (error_registers->status & 0xA5) != 0; diff --git a/worker.c b/worker.c index e682c3b..761d15a 100644 --- a/worker.c +++ b/worker.c @@ -516,9 +516,11 @@ void* WorkingLoop(void* arguments) pkt_res_scsi = (AaruPacketResScsi*)out_buf; if(sense_buf) memcpy(out_buf + sizeof(AaruPacketResScsi), sense_buf, sense_len); - if(buffer) memcpy(out_buf + sizeof(AaruPacketResScsi) + sense_len, buffer, le32toh(pkt_cmd_scsi->buf_len)); + if(buffer) + memcpy(out_buf + sizeof(AaruPacketResScsi) + sense_len, buffer, le32toh(pkt_cmd_scsi->buf_len)); - pkt_res_scsi->hdr.len = htole32(sizeof(AaruPacketResScsi) + sense_len + le32toh(pkt_cmd_scsi->buf_len)); + pkt_res_scsi->hdr.len = + htole32(sizeof(AaruPacketResScsi) + sense_len + le32toh(pkt_cmd_scsi->buf_len)); pkt_res_scsi->hdr.packet_type = AARUREMOTE_PACKET_TYPE_RESPONSE_SCSI; pkt_res_scsi->hdr.version = AARUREMOTE_PACKET_VERSION; pkt_res_scsi->hdr.remote_id = htole32(AARUREMOTE_REMOTE_ID); @@ -568,14 +570,14 @@ void* WorkingLoop(void* arguments) pkt_res_sdhci_registers->hdr.packet_type = AARUREMOTE_PACKET_TYPE_RESPONSE_GET_SDHCI_REGISTERS; pkt_res_sdhci_registers->hdr.len = htole32(sizeof(AaruPacketResGetSdhciRegisters)); pkt_res_sdhci_registers->is_sdhci = GetSdhciRegisters(device_ctx, - &csd, - &cid, - &ocr, - &scr, - &pkt_res_sdhci_registers->csd_len, - &pkt_res_sdhci_registers->cid_len, - &pkt_res_sdhci_registers->ocr_len, - &pkt_res_sdhci_registers->scr_len); + &csd, + &cid, + &ocr, + &scr, + &pkt_res_sdhci_registers->csd_len, + &pkt_res_sdhci_registers->cid_len, + &pkt_res_sdhci_registers->ocr_len, + &pkt_res_sdhci_registers->scr_len); if(pkt_res_sdhci_registers->csd_len > 0 && csd != NULL) { @@ -647,13 +649,13 @@ void* WorkingLoop(void* arguments) pkt_res_usb->hdr.packet_type = AARUREMOTE_PACKET_TYPE_RESPONSE_GET_USB_DATA; pkt_res_usb->hdr.len = htole32(sizeof(AaruPacketResGetUsbData)); pkt_res_usb->is_usb = GetUsbData(device_ctx, - &pkt_res_usb->desc_len, - pkt_res_usb->descriptors, - &pkt_res_usb->id_vendor, - &pkt_res_usb->id_product, - pkt_res_usb->manufacturer, - pkt_res_usb->product, - pkt_res_usb->serial); + &pkt_res_usb->desc_len, + pkt_res_usb->descriptors, + &pkt_res_usb->id_vendor, + &pkt_res_usb->id_product, + pkt_res_usb->manufacturer, + pkt_res_usb->product, + pkt_res_usb->serial); // Swap parameters pkt_res_usb->desc_len = htole32(pkt_res_usb->desc_len); @@ -693,11 +695,11 @@ void* WorkingLoop(void* arguments) pkt_res_firewire->hdr.packet_type = AARUREMOTE_PACKET_TYPE_RESPONSE_GET_FIREWIRE_DATA; pkt_res_firewire->hdr.len = htole32(sizeof(AaruPacketResGetFireWireData)); pkt_res_firewire->is_firewire = GetFireWireData(device_ctx, - &pkt_res_firewire->id_model, - &pkt_res_firewire->id_vendor, - &pkt_res_firewire->guid, - pkt_res_firewire->vendor, - pkt_res_firewire->model); + &pkt_res_firewire->id_model, + &pkt_res_firewire->id_vendor, + &pkt_res_firewire->guid, + pkt_res_firewire->vendor, + pkt_res_firewire->model); // TODO: Need to swap IDs? @@ -771,16 +773,16 @@ void* WorkingLoop(void* arguments) duration = 0; sense = 1; ret = SendAtaChsCommand(device_ctx, - pkt_cmd_ata_chs->registers, - &ata_chs_error_regs, - pkt_cmd_ata_chs->protocol, - pkt_cmd_ata_chs->transfer_register, - buffer, - le32toh(pkt_cmd_ata_chs->timeout), - pkt_cmd_ata_chs->transfer_blocks, - &duration, - &sense, - &pkt_cmd_ata_chs->buf_len); + pkt_cmd_ata_chs->registers, + &ata_chs_error_regs, + pkt_cmd_ata_chs->protocol, + pkt_cmd_ata_chs->transfer_register, + buffer, + le32toh(pkt_cmd_ata_chs->timeout), + pkt_cmd_ata_chs->transfer_blocks, + &duration, + &sense, + &pkt_cmd_ata_chs->buf_len); out_buf = malloc(sizeof(AaruPacketResAtaChs) + pkt_cmd_ata_chs->buf_len); @@ -843,16 +845,16 @@ void* WorkingLoop(void* arguments) duration = 0; sense = 1; ret = SendAtaLba28Command(device_ctx, - pkt_cmd_ata_lba28->registers, - &ata_lba28_error_regs, - pkt_cmd_ata_lba28->protocol, - pkt_cmd_ata_lba28->transfer_register, - buffer, - le32toh(pkt_cmd_ata_lba28->timeout), - pkt_cmd_ata_lba28->transfer_blocks, - &duration, - &sense, - &pkt_cmd_ata_lba28->buf_len); + pkt_cmd_ata_lba28->registers, + &ata_lba28_error_regs, + pkt_cmd_ata_lba28->protocol, + pkt_cmd_ata_lba28->transfer_register, + buffer, + le32toh(pkt_cmd_ata_lba28->timeout), + pkt_cmd_ata_lba28->transfer_blocks, + &duration, + &sense, + &pkt_cmd_ata_lba28->buf_len); out_buf = malloc(sizeof(AaruPacketResAtaLba28) + pkt_cmd_ata_lba28->buf_len); pkt_cmd_ata_lba28->buf_len = htole32(pkt_cmd_ata_lba28->buf_len); @@ -913,24 +915,21 @@ void* WorkingLoop(void* arguments) pkt_cmd_ata_lba48->buf_len = le32toh(pkt_cmd_ata_lba48->buf_len); // Swapping - pkt_cmd_ata_lba48->registers.lba_high = le16toh(pkt_cmd_ata_lba48->registers.lba_high); - pkt_cmd_ata_lba48->registers.lba_mid = le16toh(pkt_cmd_ata_lba48->registers.lba_mid); - pkt_cmd_ata_lba48->registers.lba_low = le16toh(pkt_cmd_ata_lba48->registers.lba_low); pkt_cmd_ata_lba48->registers.sector_count = le16toh(pkt_cmd_ata_lba48->registers.sector_count); duration = 0; sense = 1; ret = SendAtaLba48Command(device_ctx, - pkt_cmd_ata_lba48->registers, - &ata_lba48_error_regs, - pkt_cmd_ata_lba48->protocol, - pkt_cmd_ata_lba48->transfer_register, - buffer, - le32toh(pkt_cmd_ata_lba48->timeout), - pkt_cmd_ata_lba48->transfer_blocks, - &duration, - &sense, - &pkt_cmd_ata_lba48->buf_len); + pkt_cmd_ata_lba48->registers, + &ata_lba48_error_regs, + pkt_cmd_ata_lba48->protocol, + pkt_cmd_ata_lba48->transfer_register, + buffer, + le32toh(pkt_cmd_ata_lba48->timeout), + pkt_cmd_ata_lba48->transfer_blocks, + &duration, + &sense, + &pkt_cmd_ata_lba48->buf_len); out_buf = malloc(sizeof(AaruPacketResAtaLba48) + pkt_cmd_ata_lba48->buf_len); pkt_cmd_ata_lba48->buf_len = htole32(pkt_cmd_ata_lba48->buf_len); @@ -956,9 +955,6 @@ void* WorkingLoop(void* arguments) pkt_res_ata_lba48->hdr.packet_id = htole32(AARUREMOTE_PACKET_ID); // Swapping - ata_lba48_error_regs.lba_high = htole16(ata_lba48_error_regs.lba_high); - ata_lba48_error_regs.lba_mid = htole16(ata_lba48_error_regs.lba_mid); - ata_lba48_error_regs.lba_low = htole16(ata_lba48_error_regs.lba_low); ata_lba48_error_regs.sector_count = htole16(ata_lba48_error_regs.sector_count); pkt_res_ata_lba48->registers = ata_lba48_error_regs; @@ -998,19 +994,19 @@ void* WorkingLoop(void* arguments) duration = 0; sense = 1; ret = SendSdhciCommand(device_ctx, - pkt_cmd_sdhci->command.command, - pkt_cmd_sdhci->command.write, - pkt_cmd_sdhci->command.application, - le32toh(pkt_cmd_sdhci->command.flags), - le32toh(pkt_cmd_sdhci->command.argument), - le32toh(pkt_cmd_sdhci->command.block_size), - le32toh(pkt_cmd_sdhci->command.blocks), - buffer, - le32toh(pkt_cmd_sdhci->command.buf_len), - le32toh(pkt_cmd_sdhci->command.timeout), - (uint32_t*)&sdhci_response, - &duration, - &sense); + pkt_cmd_sdhci->command.command, + pkt_cmd_sdhci->command.write, + pkt_cmd_sdhci->command.application, + le32toh(pkt_cmd_sdhci->command.flags), + le32toh(pkt_cmd_sdhci->command.argument), + le32toh(pkt_cmd_sdhci->command.block_size), + le32toh(pkt_cmd_sdhci->command.blocks), + buffer, + le32toh(pkt_cmd_sdhci->command.buf_len), + le32toh(pkt_cmd_sdhci->command.timeout), + (uint32_t*)&sdhci_response, + &duration, + &sense); out_buf = malloc(sizeof(AaruPacketResSdhci) + le32toh(pkt_cmd_sdhci->command.buf_len));