Change IDE disk and ethernet device to work better with FreeBSD.
dev/ide_ctrl.cc: dev/ide_disk.cc: dev/ide_disk.hh: Add support for 32-bit accesses. dev/ns_gige.cc: Change default configuration register value to work with FreeBSD driver. --HG-- extra : convert_revision : c9dd125338a97ffa8cd95293e6b7877068652387
This commit is contained in:
parent
0460a78829
commit
8b04218262
4 changed files with 95 additions and 49 deletions
|
@ -412,14 +412,10 @@ IdeController::read(MemReqPtr &req, uint8_t *data)
|
|||
{
|
||||
Addr offset;
|
||||
bool primary;
|
||||
bool byte;
|
||||
bool cmdBlk;
|
||||
RegType_t type;
|
||||
int disk;
|
||||
|
||||
parseAddr(req->paddr, offset, primary, type);
|
||||
byte = (req->size == sizeof(uint8_t)) ? true : false;
|
||||
cmdBlk = (type == COMMAND_BLOCK) ? true : false;
|
||||
|
||||
if (!io_enabled)
|
||||
return No_Fault;
|
||||
|
@ -430,11 +426,19 @@ IdeController::read(MemReqPtr &req, uint8_t *data)
|
|||
panic("IDE controller read of invalid size: %#x\n", req->size);
|
||||
|
||||
if (type != BMI_BLOCK) {
|
||||
assert(req->size != sizeof(uint32_t));
|
||||
|
||||
disk = getDisk(primary);
|
||||
if (disks[disk])
|
||||
disks[disk]->read(offset, byte, cmdBlk, data);
|
||||
if (req->size == sizeof(uint32_t) && offset == DATA_OFFSET) {
|
||||
*((uint16_t*)data) = disks[disk]->read(offset, type);
|
||||
*((uint16_t*)data + 1) = disks[disk]->read(offset, type);
|
||||
}
|
||||
else if (req->size == sizeof(uint8_t) && offset == DATA_OFFSET) {
|
||||
panic("IDE read of data reg invalid size: %#x\n", req->size);
|
||||
}
|
||||
else {
|
||||
*data = disks[disk]->read(offset, type);
|
||||
}
|
||||
} else {
|
||||
memcpy((void *)data, &bmi_regs[offset], req->size);
|
||||
}
|
||||
|
|
120
dev/ide_disk.cc
120
dev/ide_disk.cc
|
@ -208,46 +208,61 @@ IdeDisk::bytesInDmaPage(Addr curAddr, uint32_t bytesLeft)
|
|||
// Device registers read/write
|
||||
////
|
||||
|
||||
void
|
||||
IdeDisk::read(const Addr &offset, bool byte, bool cmdBlk, uint8_t *data)
|
||||
uint16_t
|
||||
IdeDisk::read(const Addr &offset, RegType_t type)
|
||||
{
|
||||
|
||||
uint16_t data;
|
||||
DevAction_t action = ACT_NONE;
|
||||
|
||||
if (cmdBlk) {
|
||||
if (offset < 0 || offset > sizeof(CommandReg_t))
|
||||
panic("Invalid disk command register offset: %#x\n", offset);
|
||||
if (type == COMMAND_BLOCK) {
|
||||
|
||||
if (!byte && offset != DATA_OFFSET)
|
||||
panic("Invalid 16-bit read, only allowed on data reg\n");
|
||||
|
||||
if (!byte)
|
||||
*(uint16_t *)data = *(uint16_t *)&cmdReg.data0;
|
||||
else
|
||||
*data = ((uint8_t *)&cmdReg)[offset];
|
||||
|
||||
// determine if an action needs to be taken on the state machine
|
||||
if (offset == STATUS_OFFSET) {
|
||||
if (offset == STATUS_OFFSET)
|
||||
action = ACT_STAT_READ;
|
||||
*data = status; // status is in a shadow, explicity copy
|
||||
} else if (offset == DATA_OFFSET) {
|
||||
if (byte)
|
||||
action = ACT_DATA_READ_BYTE;
|
||||
else
|
||||
action = ACT_DATA_READ_SHORT;
|
||||
}
|
||||
else if (offset == DATA_OFFSET)
|
||||
action = ACT_DATA_READ_SHORT;
|
||||
|
||||
} else {
|
||||
switch (offset) {
|
||||
case DATA_OFFSET:
|
||||
data = cmdReg.data;
|
||||
break;
|
||||
case ERROR_OFFSET:
|
||||
data = cmdReg.error;
|
||||
break;
|
||||
case NSECTOR_OFFSET:
|
||||
data = cmdReg.sec_count;
|
||||
break;
|
||||
case SECTOR_OFFSET:
|
||||
data = cmdReg.sec_num;
|
||||
break;
|
||||
case LCYL_OFFSET:
|
||||
data = cmdReg.cyl_low;
|
||||
break;
|
||||
case HCYL_OFFSET:
|
||||
data = cmdReg.cyl_high;
|
||||
break;
|
||||
case SELECT_OFFSET:
|
||||
data = cmdReg.drive;
|
||||
break;
|
||||
case STATUS_OFFSET:
|
||||
data = status;
|
||||
break;
|
||||
default:
|
||||
panic("Invalid IDE command register offset: %#x\n", offset);
|
||||
}
|
||||
}
|
||||
else if (type == CONTROL_BLOCK) {
|
||||
if (offset != ALTSTAT_OFFSET)
|
||||
panic("Invalid disk control register offset: %#x\n", offset);
|
||||
panic("Invalid IDE control register offset: %#x\n", offset);
|
||||
|
||||
if (!byte)
|
||||
panic("Invalid 16-bit read from control block\n");
|
||||
|
||||
*data = status;
|
||||
data = status;
|
||||
}
|
||||
|
||||
if (action != ACT_NONE)
|
||||
updateState(action);
|
||||
|
||||
return data;
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -263,9 +278,37 @@ IdeDisk::write(const Addr &offset, bool byte, bool cmdBlk, const uint8_t *data)
|
|||
panic("Invalid 16-bit write, only allowed on data reg\n");
|
||||
|
||||
if (!byte)
|
||||
*((uint16_t *)&cmdReg.data0) = *(uint16_t *)data;
|
||||
else
|
||||
((uint8_t *)&cmdReg)[offset] = *data;
|
||||
*((uint16_t *)&cmdReg.data) = *(uint16_t *)data;
|
||||
else {
|
||||
switch (offset) {
|
||||
case DATA_OFFSET:
|
||||
cmdReg.data = *data;
|
||||
break;
|
||||
case FEATURES_OFFSET:
|
||||
cmdReg.features = *data;
|
||||
break;
|
||||
case NSECTOR_OFFSET:
|
||||
cmdReg.sec_count = *data;
|
||||
break;
|
||||
case SECTOR_OFFSET:
|
||||
cmdReg.sec_num = *data;
|
||||
break;
|
||||
case LCYL_OFFSET:
|
||||
cmdReg.cyl_low = *data;
|
||||
break;
|
||||
case HCYL_OFFSET:
|
||||
cmdReg.cyl_high = *data;
|
||||
break;
|
||||
case SELECT_OFFSET:
|
||||
cmdReg.drive = *data;
|
||||
break;
|
||||
case COMMAND_OFFSET:
|
||||
cmdReg.command = *data;
|
||||
break;
|
||||
default:
|
||||
panic("Invalid IDE command register offset: %#x\n", offset);
|
||||
}
|
||||
}
|
||||
|
||||
// determine if an action needs to be taken on the state machine
|
||||
if (offset == COMMAND_OFFSET) {
|
||||
|
@ -746,9 +789,10 @@ IdeDisk::intrPost()
|
|||
intrPending = true;
|
||||
|
||||
// talk to controller to set interrupt
|
||||
if (ctrl)
|
||||
if (ctrl){
|
||||
ctrl->bmi_regs[BMIS0] |= IDEINTS;
|
||||
ctrl->intrPost();
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -867,7 +911,7 @@ IdeDisk::updateState(DevAction_t action)
|
|||
}
|
||||
|
||||
// put the first two bytes into the data register
|
||||
memcpy((void *)&cmdReg.data0, (void *)dataBuffer,
|
||||
memcpy((void *)&cmdReg.data, (void *)dataBuffer,
|
||||
sizeof(uint16_t));
|
||||
|
||||
if (!isIENSet()) {
|
||||
|
@ -896,7 +940,7 @@ IdeDisk::updateState(DevAction_t action)
|
|||
|
||||
// copy next short into data registers
|
||||
if (drqBytesLeft)
|
||||
memcpy((void *)&cmdReg.data0,
|
||||
memcpy((void *)&cmdReg.data,
|
||||
(void *)&dataBuffer[SectorSize - drqBytesLeft],
|
||||
sizeof(uint16_t));
|
||||
}
|
||||
|
@ -969,7 +1013,7 @@ IdeDisk::updateState(DevAction_t action)
|
|||
} else {
|
||||
// copy the latest short into the data buffer
|
||||
memcpy((void *)&dataBuffer[SectorSize - drqBytesLeft],
|
||||
(void *)&cmdReg.data0,
|
||||
(void *)&cmdReg.data,
|
||||
sizeof(uint16_t));
|
||||
|
||||
drqBytesLeft -= 2;
|
||||
|
@ -1093,8 +1137,7 @@ IdeDisk::serialize(ostream &os)
|
|||
SERIALIZE_ENUM(event);
|
||||
|
||||
// Serialize device registers
|
||||
SERIALIZE_SCALAR(cmdReg.data0);
|
||||
SERIALIZE_SCALAR(cmdReg.data1);
|
||||
SERIALIZE_SCALAR(cmdReg.data);
|
||||
SERIALIZE_SCALAR(cmdReg.sec_count);
|
||||
SERIALIZE_SCALAR(cmdReg.sec_num);
|
||||
SERIALIZE_SCALAR(cmdReg.cyl_low);
|
||||
|
@ -1146,8 +1189,7 @@ IdeDisk::unserialize(Checkpoint *cp, const string §ion)
|
|||
}
|
||||
|
||||
// Unserialize device registers
|
||||
UNSERIALIZE_SCALAR(cmdReg.data0);
|
||||
UNSERIALIZE_SCALAR(cmdReg.data1);
|
||||
UNSERIALIZE_SCALAR(cmdReg.data);
|
||||
UNSERIALIZE_SCALAR(cmdReg.sec_count);
|
||||
UNSERIALIZE_SCALAR(cmdReg.sec_num);
|
||||
UNSERIALIZE_SCALAR(cmdReg.cyl_low);
|
||||
|
|
|
@ -35,6 +35,7 @@
|
|||
|
||||
#include "dev/disk_image.hh"
|
||||
#include "dev/ide_atareg.h"
|
||||
#include "dev/ide_ctrl.hh"
|
||||
#include "dev/ide_wdcreg.h"
|
||||
#include "dev/io_device.hh"
|
||||
#include "sim/eventq.hh"
|
||||
|
@ -103,9 +104,8 @@ class PrdTableEntry {
|
|||
#define DEV1 (1)
|
||||
|
||||
typedef struct CommandReg {
|
||||
uint8_t data0;
|
||||
uint16_t data;
|
||||
union {
|
||||
uint8_t data1;
|
||||
uint8_t error;
|
||||
uint8_t features;
|
||||
};
|
||||
|
@ -272,7 +272,7 @@ class IdeDisk : public SimObject
|
|||
}
|
||||
|
||||
// Device register read/write
|
||||
void read(const Addr &offset, bool byte, bool cmdBlk, uint8_t *data);
|
||||
uint16_t read(const Addr &offset, RegType_t type);
|
||||
void write(const Addr &offset, bool byte, bool cmdBlk, const uint8_t *data);
|
||||
|
||||
// Start/abort functions
|
||||
|
|
|
@ -1359,7 +1359,7 @@ void
|
|||
NSGigE::regsReset()
|
||||
{
|
||||
memset(®s, 0, sizeof(regs));
|
||||
regs.config = CFGR_LNKSTS;
|
||||
regs.config = (CFGR_LNKSTS | CFGR_TBI_EN | CFGR_MODE_1000);
|
||||
regs.mear = 0x22;
|
||||
regs.txcfg = 0x120; // set drain threshold to 1024 bytes and
|
||||
// fill threshold to 32 bytes
|
||||
|
|
Loading…
Reference in a new issue