URL
https://opencores.org/ocsvn/or1k/or1k/trunk
Subversion Repositories or1k
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 126 to Rev 127
- ↔ Reverse comparison
Rev 126 → Rev 127
/trunk/or1ksim/toplevel.c
39,6 → 39,7
#include <fcntl.h> |
#include <netdb.h> |
#include <netinet/tcp.h> |
#include <inttypes.h> |
|
#ifdef HAVE_LIBREADLINE |
#include <readline/readline.h> |
56,6 → 57,7
#include "coff.h" |
|
/* Added by CZ 24/05/01 */ |
#include "gdb.h" |
#include <signal.h> |
#include <errno.h> |
typedef enum { |
69,10 → 71,15
void HandleServerSocket(Boolean); |
void JTAGRequest(void); |
void GDBRequest(void); |
void ProtocolClean(int,int32_t); |
static int gdb_read(void*,int); |
static int gdb_write(void*,int); |
void BlockJTAG(void); |
|
int GlobalMode = 0; /* Start off in the orginal mode */ |
|
/* CVS revision number. */ |
const char rcsrev[] = "$Revision: 1.16 $"; |
const char rcsrev[] = "$Revision: 1.17 $"; |
|
/* Continuos run versus single step tracing switch. */ |
int cont_run; |
601,9 → 608,17
printf("%s: Unknown command.\n", linestr); |
} |
|
while(cont_run) { |
while(cont_run > 0) { |
extern int cycle_delay; /* Added by CZ 27/05/01. Set during exception. */ |
extern int cpu_stalled; /* CZ from debug_interface */ |
|
if(cpu_stalled) |
{ |
BlockJTAG(); |
HandleServerSocket(false); |
continue; |
} |
|
if (!getsprbits(SPR_PMR, SPR_PMR_DME | SPR_PMR_SME)) { |
if(cycle_delay <= 0) |
{ |
763,6 → 778,8
} |
} |
|
static int tcp_level = 0; |
|
/* Added by CZ 24/05/01 */ |
int GetServerSocket(const char* name,const char* proto,int port) |
{ |
782,7 → 799,8
perror(sTemp); |
return 0; |
} |
|
tcp_level = protocol->p_proto; /* Save for later */ |
|
/* If we weren't passed a non standard port, get the port |
from the services directory. */ |
if(!port) |
870,10 → 888,27
return sockfd; |
} |
|
void HandleServerSocket(Boolean block) |
void BlockJTAG() |
{ |
struct pollfd fds[2]; |
int n = 0; |
|
fds[n].fd = server_fd; |
fds[n].events = POLLIN; |
fds[n++].revents = 0; |
if(gdb_fd) |
{ |
fds[n].fd = gdb_fd; |
fds[n].events = POLLIN; |
fds[n++].revents = 0; |
} |
poll(fds,n,-1); |
} |
|
void HandleServerSocket(Boolean block) |
{ |
struct pollfd fds[3]; |
int n = 0; |
int timeout = block ? -1 : 0; |
int server_index = -1; |
int gdb_index = -1; |
916,19 → 951,7
data_on_stdin = true; /* Can only get here if nonblocking */ |
break; |
default: |
if(fds[0].revents && o_serv_fd) |
{ |
if(fds[0].revents & POLLIN) |
JTAGRequest(); |
else /* Error Occurred */ |
{ |
fprintf(stderr,"Received flags 0x%08x on server. Shutting down.\n",fds[0].revents); |
close(o_serv_fd); |
server_fd = 0; |
serverPort = 0; |
serverIP = 0; |
} |
} |
/* Make sure to handle the gdb port first! */ |
if((fds[0].revents && (gdb_fd && !o_serv_fd) || |
fds[1].revents && (server_fd && gdb_fd))) |
{ |
943,6 → 966,19
gdb_fd = 0; |
} |
} |
if(fds[0].revents && o_serv_fd) |
{ |
if(fds[0].revents & POLLIN) |
JTAGRequest(); |
else /* Error Occurred */ |
{ |
fprintf(stderr,"Received flags 0x%08x on server. Shutting down.\n",fds[0].revents); |
close(o_serv_fd); |
server_fd = 0; |
serverPort = 0; |
serverIP = 0; |
} |
} |
if(fds[2].revents || (fds[1].revents && !gdb_fd)) |
data_on_stdin = true; |
break; |
999,7 → 1035,7
return; |
} |
|
if(setsockopt(fd,SOL_TCP,TCP_NODELAY,&on_off,sizeof(int)) < 0) |
if(setsockopt(fd,tcp_level,TCP_NODELAY,&on_off,sizeof(int)) < 0) |
{ |
sprintf(sTemp,"Unable to disable Nagel's algorithm for socket %d.\nsetsockopt",fd); |
perror(sTemp); |
1012,5 → 1048,238
|
void GDBRequest() |
{ |
/* Debug interface simulation should go here. */ |
JTAGProxyWriteMessage msg_write; |
JTAGProxyReadMessage msg_read; |
JTAGProxyChainMessage msg_chain; |
JTAGProxyWriteResponse resp_write; |
JTAGProxyReadResponse resp_read; |
JTAGProxyChainResponse resp_chain; |
char *buf; |
unsigned long long data; |
int err; |
uint32_t command,length; |
|
/* First, we must read the incomming command */ |
if(gdb_read(&command,sizeof(uint32_t)) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 1"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
if(gdb_read(&length,sizeof(uint32_t)) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 2"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
length = ntohl(length); |
|
/* Now, verify the protocol and implement the command */ |
switch(ntohl(command)) |
{ |
case JTAG_COMMAND_WRITE: |
if(length != sizeof(msg_write) - 8) |
{ |
ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR); |
return; |
} |
buf = (char*)&msg_write; |
if(gdb_read(&buf[8],length) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 3"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
msg_write.address = ntohl(msg_write.address); |
msg_write.data_H = ntohl(msg_write.data_H); |
msg_write.data_L = ntohl(msg_write.data_L); |
err = DebugSetRegister(msg_write.address,msg_write.data_L); |
resp_write.status = htonl(err); |
if(gdb_write(&resp_write,sizeof(resp_write)) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 4"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
break; |
case JTAG_COMMAND_READ: |
if(length != sizeof(msg_read) - 8) |
{ |
ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR); |
return; |
} |
buf = (char*)&msg_read; |
if(gdb_read(&buf[8],length) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 5"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
msg_read.address = ntohl(msg_read.address); |
err = DebugGetRegister(msg_read.address,&resp_read.data_L); |
resp_read.status = htonl(err); |
resp_read.data_H = 0; |
resp_read.data_L = htonl(resp_read.data_L); |
if(gdb_write(&resp_read,sizeof(resp_read)) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 6"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
break; |
case JTAG_COMMAND_CHAIN: |
if(length != sizeof(msg_chain) - 8) |
{ |
ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR); |
return; |
} |
buf = (char*)&msg_chain; |
if(gdb_read(&buf[8],sizeof(msg_chain)-8) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 7"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
msg_chain.chain = htonl(msg_chain.chain); |
err = DebugSetChain(msg_chain.chain); |
resp_chain.status = htonl(err); |
if(gdb_write(&resp_chain,sizeof(resp_chain)) < 0) |
{ |
if(gdb_fd) |
{ |
perror("gdb socket - 8"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
return; |
} |
break; |
default: |
ProtocolClean(length,JTAG_PROXY_COMMAND_NOT_IMPLEMENTED); |
break; |
} |
} |
|
void ProtocolClean(int length,int32_t err) |
{ |
char buf[4096]; |
|
err = htonl(err); |
if((gdb_read(buf,length) < 0) || |
(gdb_write(&err,sizeof(err)) < 0) && gdb_fd) |
{ |
perror("gdb socket - 9"); |
close(gdb_fd); |
gdb_fd = 0; |
} |
} |
|
static int gdb_write(void* buf,int len) |
{ |
int n; |
char* w_buf = (char*)buf; |
struct pollfd block; |
|
while(len) |
{ |
if((n = write(gdb_fd,w_buf,len)) < 0) |
{ |
switch(errno) |
{ |
case EWOULDBLOCK: /* or EAGAIN */ |
/* We've been called on a descriptor marked |
for nonblocking I/O. We better simulate |
blocking behavior. */ |
block.fd = gdb_fd; |
block.events = POLLOUT; |
block.revents = 0; |
poll(&block,1,-1); |
continue; |
case EINTR: |
continue; |
case EPIPE: |
close(gdb_fd); |
gdb_fd = 0; |
return -1; |
default: |
return -1; |
} |
} |
else |
{ |
len -= n; |
w_buf += n; |
} |
} |
return 0; |
} |
|
static int gdb_read(void* buf,int len) |
{ |
int n; |
char* r_buf = (char*)buf; |
struct pollfd block; |
|
while(len) |
{ |
if((n = read(gdb_fd,r_buf,len)) < 0) |
{ |
switch(errno) |
{ |
case EWOULDBLOCK: /* or EAGAIN */ |
/* We've been called on a descriptor marked |
for nonblocking I/O. We better simulate |
blocking behavior. */ |
block.fd = gdb_fd; |
block.events = POLLIN; |
block.revents = 0; |
poll(&block,1,-1); |
continue; |
case EINTR: |
continue; |
default: |
return -1; |
} |
} |
else if(n == 0) |
{ |
close(gdb_fd); |
gdb_fd = 0; |
return -1; |
} |
else |
{ |
len -= n; |
r_buf += n; |
} |
} |
return 0; |
} |