Browse Source

implement lighter-weight htif packet header

eos18-bringup
Andrew Waterman 15 years ago
parent
commit
1536af0c02
  1. 54
      riscv/htif.cc
  2. 4
      riscv/htif.h

54
riscv/htif.cc

@ -21,14 +21,15 @@ enum
APP_CMD_NACK
};
#define APP_DATA_ALIGN 8
#define APP_MAX_DATA_SIZE 1024
#define HTIF_DATA_ALIGN 8
struct packet
{
uint16_t cmd;
uint16_t seqno;
uint32_t data_size;
uint64_t addr;
reg_t cmd : 4;
reg_t data_size : 12;
reg_t seqno : 8;
reg_t addr : 40;
uint8_t data[APP_MAX_DATA_SIZE];
};
@ -65,18 +66,19 @@ void htif_t::wait_for_fromhost_write()
void htif_t::send_packet(packet* p)
{
int bytes = write(tohost_fd,p,offsetof(packet,data)+p->data_size);
if((size_t)bytes != offsetof(packet,data) + p->data_size)
size_t data_size = p->data_size*HTIF_DATA_ALIGN;
size_t bytes = write(tohost_fd, p, offsetof(packet,data) + data_size);
if(bytes != offsetof(packet,data) + data_size)
{
const char* error = bytes == -1 ? strerror(errno) : "not all bytes sent";
const char* error = (ssize_t)bytes == -1 ? strerror(errno) : "not all bytes sent";
fprintf(stderr,"HTIF error: %s\n", error);
exit(-1);
}
}
void htif_t::nack(uint16_t nack_seqno)
void htif_t::nack(uint8_t nack_seqno)
{
packet p = {APP_CMD_NACK,nack_seqno,0,0};
packet p = {APP_CMD_NACK,0,nack_seqno,0};
send_packet(&p);
}
@ -110,7 +112,7 @@ int htif_t::wait_for_packet()
continue;
}
packet ackpacket = {APP_CMD_ACK,seqno,0,0};
packet ackpacket = {APP_CMD_ACK,0,seqno,0};
switch(p.cmd)
{
@ -120,34 +122,32 @@ int htif_t::wait_for_packet()
sim->stop();
break;
case APP_CMD_READ_MEM:
assert(p.addr % APP_DATA_ALIGN == 0);
assert(p.data_size % APP_DATA_ALIGN == 0);
assert(p.data_size <= APP_MAX_DATA_SIZE);
assert(p.addr <= sim->memsz && p.addr+p.data_size <= sim->memsz);
assert(p.data_size <= APP_MAX_DATA_SIZE/HTIF_DATA_ALIGN);
assert(p.addr < sim->memsz/HTIF_DATA_ALIGN);
assert(p.addr+p.data_size <= sim->memsz/HTIF_DATA_ALIGN);
ackpacket.data_size = p.data_size;
static_assert(APP_DATA_ALIGN >= sizeof(uint64_t))
for(size_t i = 0; i < p.data_size/8; i++)
((uint64_t*)ackpacket.data)[i] = sim->mmu->load_uint64(p.addr+i*8);
assert(HTIF_DATA_ALIGN == sizeof(uint64_t));
for(size_t i = 0; i < p.data_size; i++)
((uint64_t*)ackpacket.data)[i] = sim->mmu->load_uint64((p.addr+i)*HTIF_DATA_ALIGN);
break;
case APP_CMD_WRITE_MEM:
assert(p.addr % APP_DATA_ALIGN == 0);
assert(p.data_size % APP_DATA_ALIGN == 0);
assert(p.data_size <= bytes - offsetof(packet,data));
assert(p.addr <= sim->memsz && p.addr+p.data_size <= sim->memsz);
assert(p.data_size*HTIF_DATA_ALIGN <= bytes - offsetof(packet,data));
assert(p.addr < sim->memsz/HTIF_DATA_ALIGN);
assert(p.addr+p.data_size <= sim->memsz/HTIF_DATA_ALIGN);
for(size_t i = 0; i < p.data_size/8; i++)
sim->mmu->store_uint64(p.addr+i*8, ((uint64_t*)p.data)[i]);
for(size_t i = 0; i < p.data_size; i++)
sim->mmu->store_uint64((p.addr+i)*HTIF_DATA_ALIGN, ((uint64_t*)p.data)[i]);
break;
case APP_CMD_READ_CONTROL_REG:
assert(p.addr == 16);
assert(p.data_size == sizeof(reg_t));
ackpacket.data_size = sizeof(reg_t);
assert(p.data_size == 1);
ackpacket.data_size = 1;
memcpy(ackpacket.data,&sim->tohost,sizeof(reg_t));
break;
case APP_CMD_WRITE_CONTROL_REG:
assert(p.addr == 17);
assert(p.data_size == sizeof(reg_t));
assert(p.data_size == 1);
sim->tohost = 0;
memcpy(&sim->fromhost,p.data,sizeof(reg_t));
break;

4
riscv/htif.h

@ -29,9 +29,9 @@ private:
sim_t* sim;
int tohost_fd;
int fromhost_fd;
uint16_t seqno;
uint8_t seqno;
void nack(uint16_t seqno);
void nack(uint8_t seqno);
void send_packet(packet* p);
int wait_for_packet();
};

Loading…
Cancel
Save