mirror of
https://github.com/aap/pdp6.git
synced 2026-05-04 15:15:49 +00:00
emu: implemented basic command line interface; sav loader
This commit is contained in:
@@ -1,4 +1,5 @@
|
|||||||
SRC=main.c apr.c mem.c tty.c pt.c
|
SRC=main.c cmd.c apr.c mem.c tty.c pt.c ../tools/pdp6common.c
|
||||||
|
H=pdp6.h ../tools/pdp6common.h
|
||||||
# clang
|
# clang
|
||||||
#CFLAGS= -Wno-shift-op-parentheses -Wno-logical-op-parentheses \
|
#CFLAGS= -Wno-shift-op-parentheses -Wno-logical-op-parentheses \
|
||||||
# -Wno-bitwise-op-parentheses
|
# -Wno-bitwise-op-parentheses
|
||||||
@@ -8,6 +9,6 @@ CFLAGS= -g -fno-diagnostics-show-caret \
|
|||||||
LIBS= `sdl-config --libs` `pkg-config SDL_image --libs` -lpthread
|
LIBS= `sdl-config --libs` `pkg-config SDL_image --libs` -lpthread
|
||||||
|
|
||||||
|
|
||||||
pdp6: $(SRC) pdp6.h
|
pdp6: $(SRC) $(H)
|
||||||
$(CC) $(CFLAGS) $(SRC) $(LIBS) -o pdp6
|
$(CC) $(CFLAGS) $(SRC) $(LIBS) -o pdp6
|
||||||
|
|
||||||
|
|||||||
@@ -3034,11 +3034,15 @@ nextpulse(Apr *apr, Pulse *p)
|
|||||||
apr->nlist[apr->nnextpulses++] = p;
|
apr->nlist[apr->nnextpulses++] = p;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
Apr*
|
||||||
initapr(Apr *apr)
|
makeapr(void)
|
||||||
{
|
{
|
||||||
|
Apr *apr;
|
||||||
|
apr = malloc(sizeof(Apr));
|
||||||
|
memset(apr, 0, sizeof(Apr));
|
||||||
apr->iobus.dev[CPA] = (Busdev){ apr, wake_cpa, 0 };
|
apr->iobus.dev[CPA] = (Busdev){ apr, wake_cpa, 0 };
|
||||||
apr->iobus.dev[PI] = (Busdev){ apr, wake_pi, 0 };
|
apr->iobus.dev[PI] = (Busdev){ apr, wake_pi, 0 };
|
||||||
|
return apr;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* find out which bits were turned on */
|
/* find out which bits were turned on */
|
||||||
|
|||||||
377
emu/cmd.c
Normal file
377
emu/cmd.c
Normal file
@@ -0,0 +1,377 @@
|
|||||||
|
#include "pdp6.h"
|
||||||
|
#include "args.h"
|
||||||
|
|
||||||
|
#define MAXOPS 20
|
||||||
|
|
||||||
|
static char *lp;
|
||||||
|
static int numops;
|
||||||
|
static char *ops[MAXOPS];
|
||||||
|
|
||||||
|
/* current apr */
|
||||||
|
static Apr *apr;
|
||||||
|
|
||||||
|
static void
|
||||||
|
skipwhite(void)
|
||||||
|
{
|
||||||
|
while(isspace(*lp))
|
||||||
|
lp++;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
isdelim(char c)
|
||||||
|
{
|
||||||
|
return c && strchr(" \t\n;'\"", c) != nil;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* tokenize lp into ops[numops] */
|
||||||
|
static void
|
||||||
|
splitops(void)
|
||||||
|
{
|
||||||
|
char delim;
|
||||||
|
char *p;
|
||||||
|
|
||||||
|
numops = 0;
|
||||||
|
for(; *lp; lp++){
|
||||||
|
skipwhite();
|
||||||
|
if(*lp == ';' || *lp == '\0')
|
||||||
|
return;
|
||||||
|
if(numops == MAXOPS){
|
||||||
|
fprintf(stderr, "Too many arguments, ignored <%s>\n", lp);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if(*lp == '"' || *lp == '\''){
|
||||||
|
delim = *lp++;
|
||||||
|
ops[numops++] = p = lp;
|
||||||
|
while(*lp && *lp != delim){
|
||||||
|
if(*lp == '\\')
|
||||||
|
lp++;
|
||||||
|
*p++ = *lp++;
|
||||||
|
}
|
||||||
|
*p = '\0';
|
||||||
|
}else{
|
||||||
|
ops[numops++] = p = lp;
|
||||||
|
while(!isdelim(*lp)){
|
||||||
|
if(*lp == '\\')
|
||||||
|
lp++;
|
||||||
|
*p++ = *lp++;
|
||||||
|
}
|
||||||
|
*p = '\0';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Parse an octal, decimal or hexadecimal number.
|
||||||
|
* 0nnnn is an octal number.
|
||||||
|
* nnnn. is a decimal number.
|
||||||
|
* 0xnnnn is a hexadecimal number.
|
||||||
|
* returns ~0 on error.
|
||||||
|
*/
|
||||||
|
word
|
||||||
|
parsen(char **sp)
|
||||||
|
{
|
||||||
|
char *s;
|
||||||
|
word dec, oct, hex;
|
||||||
|
char c;
|
||||||
|
int base;
|
||||||
|
|
||||||
|
s = *sp;
|
||||||
|
base = 0;
|
||||||
|
dec = oct = hex = 0;
|
||||||
|
if(s[0] == '0'){
|
||||||
|
s++;
|
||||||
|
base = 8;
|
||||||
|
if(*s == 'x' || *s == 'X'){
|
||||||
|
s++;
|
||||||
|
base = 16;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while(c = *s++){
|
||||||
|
if(c >= '0' && c <= '9')
|
||||||
|
c -= '0';
|
||||||
|
else if(c >= 'A' && c <= 'F')
|
||||||
|
c -= 'A' + 10;
|
||||||
|
else if(c >= 'a' && c <= 'f')
|
||||||
|
c -= 'a' + 10;
|
||||||
|
else if(c == '.'){
|
||||||
|
/* decimal number, but only if . is at the end */
|
||||||
|
if(base <= 10 && *s == '\0'){
|
||||||
|
base = 10;
|
||||||
|
break;
|
||||||
|
}else
|
||||||
|
goto fail;
|
||||||
|
}else
|
||||||
|
break;
|
||||||
|
oct = oct*8 + c;
|
||||||
|
dec = dec*10 + c;
|
||||||
|
hex = hex*16 + c;
|
||||||
|
if(c >= 8){
|
||||||
|
if(base < 8)
|
||||||
|
base = 8;
|
||||||
|
else
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
if(c >= 10){
|
||||||
|
if(base < 10)
|
||||||
|
base = 10;
|
||||||
|
else
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
if(c >= 16){
|
||||||
|
if(base < 16)
|
||||||
|
base = 16;
|
||||||
|
else
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*sp = s-1;
|
||||||
|
if(base == 16) return hex;
|
||||||
|
if(base == 10) return dec;
|
||||||
|
return oct;
|
||||||
|
fail:
|
||||||
|
printf("error: number format\n");
|
||||||
|
return ~0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
parserange(char *s, word *start, word *end)
|
||||||
|
{
|
||||||
|
*start = *end = ~0;
|
||||||
|
|
||||||
|
*start = parsen(&s);
|
||||||
|
if(*start == ~0) return 1;
|
||||||
|
|
||||||
|
if(*s == '\0'){
|
||||||
|
*end = *start;
|
||||||
|
return 0;
|
||||||
|
}else if(*s == '-' || *s == ':'){
|
||||||
|
s++;
|
||||||
|
*end = parsen(&s);
|
||||||
|
if(*end == ~0) return 1;
|
||||||
|
}
|
||||||
|
if(*s){
|
||||||
|
*start = *end = ~0;
|
||||||
|
printf("error: address format\n");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
FmtOct, FmtMnem
|
||||||
|
};
|
||||||
|
|
||||||
|
static void
|
||||||
|
exam(word addr, int fastmem, int format)
|
||||||
|
{
|
||||||
|
word *p;
|
||||||
|
p = getmemref(&apr->membus, addr, fastmem);
|
||||||
|
if(p == nil){
|
||||||
|
printf("Non existent memory\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
printf("%06lo: ", addr);
|
||||||
|
switch(format){
|
||||||
|
case FmtOct:
|
||||||
|
default:
|
||||||
|
printf("%012lo\n", *p);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case FmtMnem:
|
||||||
|
printf("%s\n", disasm(*p));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
dep(word addr, int fastmem, word w)
|
||||||
|
{
|
||||||
|
word *p;
|
||||||
|
p = getmemref(&apr->membus, addr, fastmem);
|
||||||
|
if(p == nil){
|
||||||
|
printf("Non existent memory\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
*p = w;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Commands */
|
||||||
|
|
||||||
|
static void
|
||||||
|
c_ex(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
char *argv0;
|
||||||
|
word start, end;
|
||||||
|
int format, fastmem;
|
||||||
|
|
||||||
|
format = FmtOct;
|
||||||
|
fastmem = 1;
|
||||||
|
ARGBEGIN{
|
||||||
|
case 's': /* shadow mode */
|
||||||
|
fastmem = 0;
|
||||||
|
break;
|
||||||
|
case 'm':
|
||||||
|
format = FmtMnem;
|
||||||
|
break;
|
||||||
|
}ARGEND;
|
||||||
|
if(argc < 1)
|
||||||
|
return;
|
||||||
|
if(parserange(argv[0], &start, &end))
|
||||||
|
return;
|
||||||
|
for(; start <= end; start++)
|
||||||
|
exam(start, fastmem, format);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
c_dep(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
char *argv0;
|
||||||
|
word start, end;
|
||||||
|
word w;
|
||||||
|
int fastmem;
|
||||||
|
|
||||||
|
fastmem = 1;
|
||||||
|
ARGBEGIN{
|
||||||
|
case 's':
|
||||||
|
fastmem = 0;
|
||||||
|
break;
|
||||||
|
}ARGEND;
|
||||||
|
if(argc < 2)
|
||||||
|
return;
|
||||||
|
if(parserange(argv[0], &start, &end))
|
||||||
|
return;
|
||||||
|
w = parsen(&argv[1]);
|
||||||
|
if(w == ~0)
|
||||||
|
return;
|
||||||
|
for(; start <= end; start++)
|
||||||
|
dep(start, fastmem, w);
|
||||||
|
}
|
||||||
|
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
FmtUnk, FmtSav
|
||||||
|
};
|
||||||
|
|
||||||
|
static void
|
||||||
|
loadsav(FILE *fp)
|
||||||
|
{
|
||||||
|
word iowd;
|
||||||
|
word w;
|
||||||
|
while(w = readwbak(fp), w != ~0){
|
||||||
|
if(w >> 27 == 0254){
|
||||||
|
apr->pc = right(w);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
iowd = w;
|
||||||
|
while(left(iowd) != 0){
|
||||||
|
iowd += 01000001;
|
||||||
|
w = readwbak(fp);
|
||||||
|
if(w == ~0)
|
||||||
|
return;
|
||||||
|
dep(right(iowd), 0, w);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
c_load(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
FILE *fp;
|
||||||
|
int fmt;
|
||||||
|
|
||||||
|
fmt = FmtSav; // assume SAV for now
|
||||||
|
ARGBEGIN{
|
||||||
|
case 's':
|
||||||
|
fmt = FmtSav;
|
||||||
|
break;
|
||||||
|
}ARGEND;
|
||||||
|
if(argc < 1)
|
||||||
|
return;
|
||||||
|
|
||||||
|
fp = fopen(argv[0], "rb");
|
||||||
|
if(fp == nil){
|
||||||
|
printf("couldn't open file: %s\n", argv[0]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if(fmt == FmtSav)
|
||||||
|
loadsav(fp);
|
||||||
|
fclose(fp);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
c_show(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
printf("Memory:\n");
|
||||||
|
showmem(&apr->membus);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
c_quit(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
quit(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
struct {
|
||||||
|
char *cmd;
|
||||||
|
void (*f)(int, char **);
|
||||||
|
} cmdtab[] = {
|
||||||
|
{ "examine", c_ex },
|
||||||
|
{ "deposit", c_dep },
|
||||||
|
{ "load", c_load },
|
||||||
|
{ "show", c_show },
|
||||||
|
{ "quit", c_quit },
|
||||||
|
{ "", nil}
|
||||||
|
};
|
||||||
|
|
||||||
|
void*
|
||||||
|
cmdthread(void *p)
|
||||||
|
{
|
||||||
|
size_t len, l;
|
||||||
|
char *line, *cmd;
|
||||||
|
int i, n;
|
||||||
|
int nfound;
|
||||||
|
|
||||||
|
apr = nil;
|
||||||
|
for(i = 0; i < 4; i++)
|
||||||
|
if(aprs[i]){
|
||||||
|
apr = aprs[i];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
for(;;){
|
||||||
|
line = nil;
|
||||||
|
len = 0;
|
||||||
|
printf("> ");
|
||||||
|
if(getline(&line, &len, stdin) < 0)
|
||||||
|
quit(0);
|
||||||
|
|
||||||
|
lp = line;
|
||||||
|
splitops();
|
||||||
|
|
||||||
|
if(numops){
|
||||||
|
nfound = 0;
|
||||||
|
for(i = 0; cmdtab[i].cmd[0]; i++){
|
||||||
|
cmd = cmdtab[i].cmd;
|
||||||
|
l = strlen(ops[0]);
|
||||||
|
if(strncmp(ops[0], cmd, l) == 0){
|
||||||
|
n = i;
|
||||||
|
nfound++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(nfound == 0)
|
||||||
|
printf("%s: not found\n", ops[0]);
|
||||||
|
else if(nfound == 1)
|
||||||
|
cmdtab[n].f(numops, ops);
|
||||||
|
else{
|
||||||
|
printf("Ambiguous command: %s\n", ops[0]);
|
||||||
|
for(i = 0; cmdtab[i].cmd[0]; i++){
|
||||||
|
cmd = cmdtab[i].cmd;
|
||||||
|
l = strlen(ops[0]);
|
||||||
|
if(strncmp(ops[0], cmd, l) == 0)
|
||||||
|
printf(" %s\n", cmd);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
free(line);
|
||||||
|
}
|
||||||
|
return nil;
|
||||||
|
}
|
||||||
57
emu/main.c
57
emu/main.c
@@ -534,6 +534,14 @@ getms(void)
|
|||||||
return SDL_GetTicks();
|
return SDL_GetTicks();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
quit(int code)
|
||||||
|
{
|
||||||
|
//SDL_Quit();
|
||||||
|
putchar('\n');
|
||||||
|
exit(code);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
usage(void)
|
usage(void)
|
||||||
{
|
{
|
||||||
@@ -541,10 +549,7 @@ usage(void)
|
|||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
Apr apr;
|
Apr *aprs[4];
|
||||||
Tty tty;
|
|
||||||
Ptr ptr;
|
|
||||||
Ptp ptp;
|
|
||||||
Mem *coremems[4];
|
Mem *coremems[4];
|
||||||
|
|
||||||
int
|
int
|
||||||
@@ -559,8 +564,14 @@ main(int argc, char *argv[])
|
|||||||
int delay;
|
int delay;
|
||||||
int i;
|
int i;
|
||||||
int w, h;
|
int w, h;
|
||||||
|
pthread_t cmd_thread;
|
||||||
const char *outfile, *ttyfile;
|
const char *outfile, *ttyfile;
|
||||||
|
|
||||||
|
Apr *apr;
|
||||||
|
Ptr *ptr;
|
||||||
|
Ptp *ptp;
|
||||||
|
Tty *tty;
|
||||||
|
|
||||||
outfile = "/dev/null";
|
outfile = "/dev/null";
|
||||||
ttyfile = "/tmp/6tty";
|
ttyfile = "/tmp/6tty";
|
||||||
ARGBEGIN{
|
ARGBEGIN{
|
||||||
@@ -670,22 +681,23 @@ main(int argc, char *argv[])
|
|||||||
|
|
||||||
extra_l = e; e += 1;
|
extra_l = e; e += 1;
|
||||||
|
|
||||||
initapr(&apr);
|
aprs[0] = apr = makeapr();
|
||||||
coremems[0] = makecoremem("mem_0");
|
coremems[0] = makecoremem("mem_0");
|
||||||
coremems[1] = makecoremem("mem_1");
|
coremems[1] = makecoremem("mem_1");
|
||||||
coremems[2] = makecoremem("mem_2");
|
coremems[2] = makecoremem("mem_2");
|
||||||
coremems[3] = makecoremem("mem_3");
|
coremems[3] = makecoremem("mem_3");
|
||||||
attachmem(makefastmem(0), 0, &apr.membus, -1);
|
attachmem(makefastmem(0), 0, &apr->membus, -1);
|
||||||
attachmem(coremems[0], 0, &apr.membus, 0);
|
attachmem(coremems[0], 0, &apr->membus, 0);
|
||||||
attachmem(coremems[1], 0, &apr.membus, 1);
|
attachmem(coremems[1], 0, &apr->membus, 1);
|
||||||
attachmem(coremems[2], 0, &apr.membus, 2);
|
attachmem(coremems[2], 0, &apr->membus, 2);
|
||||||
attachmem(coremems[3], 0, &apr.membus, 3);
|
attachmem(coremems[3], 0, &apr->membus, 3);
|
||||||
inittty(&tty, &apr.iobus);
|
tty = maketty(&apr->iobus);
|
||||||
initptr(&ptr, &apr.iobus);
|
ptr = makeptr(&apr->iobus);
|
||||||
initptp(&ptp, &apr.iobus);
|
ptp = makeptp(&apr->iobus);
|
||||||
if(ttyfile)
|
if(ttyfile)
|
||||||
attachdevtty(&tty, ttyfile);
|
attachdevtty(tty, ttyfile);
|
||||||
showmem(&apr.membus);
|
|
||||||
|
pthread_create(&cmd_thread, nil, cmdthread, nil);
|
||||||
|
|
||||||
for(;;){
|
for(;;){
|
||||||
start = SDL_GetTicks();
|
start = SDL_GetTicks();
|
||||||
@@ -701,13 +713,12 @@ main(int argc, char *argv[])
|
|||||||
mouse(mbev->button, mbev->state, mbev->x, mbev->y);
|
mouse(mbev->button, mbev->state, mbev->x, mbev->y);
|
||||||
break;
|
break;
|
||||||
case SDL_QUIT:
|
case SDL_QUIT:
|
||||||
SDL_Quit();
|
quit(0);
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
updateapr(&apr, &ptr);
|
updateapr(apr, ptr);
|
||||||
updatetty(&tty);
|
updatetty(tty);
|
||||||
updatept(&ptp, &ptr);
|
updatept(ptp, ptr);
|
||||||
|
|
||||||
SDL_FillRect(screen, nil, SDL_MapRGBA(screen->format, 0xe6, 0xe6, 0xe6, 0xff));
|
SDL_FillRect(screen, nil, SDL_MapRGBA(screen->format, 0xe6, 0xe6, 0xe6, 0xff));
|
||||||
SDL_BlitSurface(indpanel1.surf, nil, screen, &indpanel1.pos);
|
SDL_BlitSurface(indpanel1.surf, nil, screen, &indpanel1.pos);
|
||||||
@@ -717,11 +728,11 @@ main(int argc, char *argv[])
|
|||||||
SDL_BlitSurface(oppanel.surf, nil, screen, &oppanel.pos);
|
SDL_BlitSurface(oppanel.surf, nil, screen, &oppanel.pos);
|
||||||
|
|
||||||
for(i = 0, e = lamps; i < nelem(lamps); i++, e++)
|
for(i = 0, e = lamps; i < nelem(lamps); i++, e++)
|
||||||
drawelement(screen, e, apr.sw_power);
|
drawelement(screen, e, apr->sw_power);
|
||||||
for(i = 0, e = keys; i < nelem(keys); i++, e++)
|
for(i = 0, e = keys; i < nelem(keys); i++, e++)
|
||||||
drawelement(screen, e, apr.sw_power);
|
drawelement(screen, e, apr->sw_power);
|
||||||
for(i = 0, e = switches; i < nelem(switches); i++, e++)
|
for(i = 0, e = switches; i < nelem(switches); i++, e++)
|
||||||
drawelement(screen, e, apr.sw_power);
|
drawelement(screen, e, apr->sw_power);
|
||||||
|
|
||||||
// SDL_LockSurface(screen);
|
// SDL_LockSurface(screen);
|
||||||
// drawgrid(&opgrid1, screen, 0xFFFFFF00);
|
// drawgrid(&opgrid1, screen, 0xFFFFFF00);
|
||||||
|
|||||||
20
emu/mem.c
20
emu/mem.c
@@ -239,6 +239,7 @@ makecoremem(const char *file)
|
|||||||
Mem *mem;
|
Mem *mem;
|
||||||
|
|
||||||
core = malloc(sizeof(CMem));
|
core = malloc(sizeof(CMem));
|
||||||
|
memset(core, 0, sizeof(CMem));
|
||||||
core->filename = file;
|
core->filename = file;
|
||||||
pthread_mutex_init(&core->mutex, nil);
|
pthread_mutex_init(&core->mutex, nil);
|
||||||
|
|
||||||
@@ -303,6 +304,23 @@ showmem(Membus *bus)
|
|||||||
for(i = 0; i < 16; i++)
|
for(i = 0; i < 16; i++)
|
||||||
if(bus->cmem[i]){
|
if(bus->cmem[i]){
|
||||||
core = bus->cmem[i]->module;
|
core = bus->cmem[i]->module;
|
||||||
printf("%06o %06o %s\n", i<<14, (i+1 << 14)-1, core->filename);
|
printf("%s: %06o %06o\n", core->filename, i<<14, (i+1 << 14)-1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
word*
|
||||||
|
getmemref(Membus *bus, hword addr, int fastmem)
|
||||||
|
{
|
||||||
|
CMem *core;
|
||||||
|
FMem *ff;
|
||||||
|
|
||||||
|
if(fastmem && addr < 020 && bus->fmem){
|
||||||
|
ff = bus->fmem->module;
|
||||||
|
return &ff->ff[addr];
|
||||||
|
}
|
||||||
|
if(bus->cmem[addr>>14]){
|
||||||
|
core = bus->cmem[addr>>14]->module;
|
||||||
|
return &core->core[addr & 037777];
|
||||||
|
}
|
||||||
|
return nil;
|
||||||
|
}
|
||||||
|
|||||||
17
emu/pdp6.h
17
emu/pdp6.h
@@ -3,16 +3,16 @@
|
|||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdarg.h>
|
#include <stdarg.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
#include <ctype.h>
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
#include <pthread.h>
|
#include <pthread.h>
|
||||||
|
#include "../tools/pdp6common.h"
|
||||||
|
|
||||||
#define nelem(a) (sizeof(a)/sizeof(a[0]))
|
#define nelem(a) (sizeof(a)/sizeof(a[0]))
|
||||||
#define nil NULL
|
#define nil NULL
|
||||||
#define print printf
|
#define print printf
|
||||||
#define fprint fprintf
|
#define fprint fprintf
|
||||||
|
|
||||||
typedef uint64_t word;
|
|
||||||
typedef uint32_t hword;
|
|
||||||
typedef uint32_t u32;
|
typedef uint32_t u32;
|
||||||
typedef uint16_t u16;
|
typedef uint16_t u16;
|
||||||
typedef int8_t i8;
|
typedef int8_t i8;
|
||||||
@@ -25,6 +25,9 @@ extern int dotrace;
|
|||||||
void trace(char *fmt, ...);
|
void trace(char *fmt, ...);
|
||||||
void debug(char *fmt, ...);
|
void debug(char *fmt, ...);
|
||||||
|
|
||||||
|
void quit(int code);
|
||||||
|
void *cmdthread(void *);
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
MAXPULSE = 5
|
MAXPULSE = 5
|
||||||
};
|
};
|
||||||
@@ -203,6 +206,7 @@ Mem *makecoremem(const char *file);
|
|||||||
void attachmem(Mem *mem, int p, Membus *bus, int n);
|
void attachmem(Mem *mem, int p, Membus *bus, int n);
|
||||||
void readmem(const char *file, word *mem, word size);
|
void readmem(const char *file, word *mem, word size);
|
||||||
void showmem(Membus *bus);
|
void showmem(Membus *bus);
|
||||||
|
word *getmemref(Membus *bus, hword addr, int fastmem);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* IO bus
|
* IO bus
|
||||||
@@ -395,7 +399,8 @@ struct Apr
|
|||||||
Pulse **clist, **nlist;
|
Pulse **clist, **nlist;
|
||||||
int ncurpulses, nnextpulses;
|
int ncurpulses, nnextpulses;
|
||||||
};
|
};
|
||||||
void initapr(Apr *apr);
|
extern Apr *aprs[4];
|
||||||
|
Apr *makeapr(void);
|
||||||
void curpulse(Apr *apr, Pulse *p);
|
void curpulse(Apr *apr, Pulse *p);
|
||||||
void nextpulse(Apr *apr, Pulse *p);
|
void nextpulse(Apr *apr, Pulse *p);
|
||||||
void *aprmain(void *p);
|
void *aprmain(void *p);
|
||||||
@@ -414,7 +419,7 @@ struct Ptp
|
|||||||
FILE *fp;
|
FILE *fp;
|
||||||
int waitdatao;
|
int waitdatao;
|
||||||
};
|
};
|
||||||
void initptp(Ptp *ptp, IOBus *bus);
|
Ptp *makeptp(IOBus *bus);
|
||||||
|
|
||||||
|
|
||||||
/* Paper tape reader 760 */
|
/* Paper tape reader 760 */
|
||||||
@@ -431,7 +436,7 @@ struct Ptr
|
|||||||
|
|
||||||
FILE *fp;
|
FILE *fp;
|
||||||
};
|
};
|
||||||
void initptr(Ptr *ptr, IOBus *bus);
|
Ptr *makeptr(IOBus *bus);
|
||||||
void ptr_setmotor(Ptr *ptr, int m);
|
void ptr_setmotor(Ptr *ptr, int m);
|
||||||
|
|
||||||
|
|
||||||
@@ -447,7 +452,7 @@ struct Tty
|
|||||||
int pia;
|
int pia;
|
||||||
int fd;
|
int fd;
|
||||||
};
|
};
|
||||||
void inittty(Tty *tty, IOBus *bus);
|
Tty *maketty(IOBus *bus);
|
||||||
void attachdevtty(Tty *tty, const char *path);
|
void attachdevtty(Tty *tty, const char *path);
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
17
emu/pt.c
17
emu/pt.c
@@ -190,21 +190,30 @@ ptr_setmotor(Ptr *ptr, int m)
|
|||||||
recalc_ptr_req(ptr);
|
recalc_ptr_req(ptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
Ptp*
|
||||||
initptp(Ptp *ptp, IOBus *bus)
|
makeptp(IOBus *bus)
|
||||||
{
|
{
|
||||||
pthread_t thread_id;
|
pthread_t thread_id;
|
||||||
|
Ptp *ptp;
|
||||||
|
|
||||||
|
ptp = malloc(sizeof(Ptp));
|
||||||
|
memset(ptp, 0, sizeof(Ptp));
|
||||||
ptp->bus = bus;
|
ptp->bus = bus;
|
||||||
bus->dev[PTP] = (Busdev){ ptp, wake_ptp, 0 };
|
bus->dev[PTP] = (Busdev){ ptp, wake_ptp, 0 };
|
||||||
pthread_create(&thread_id, nil, ptpthread, ptp);
|
pthread_create(&thread_id, nil, ptpthread, ptp);
|
||||||
|
|
||||||
ptp->fp = fopen("../code/ptp.out", "wb");
|
ptp->fp = fopen("../code/ptp.out", "wb");
|
||||||
|
return ptp;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
Ptr*
|
||||||
initptr(Ptr *ptr, IOBus *bus)
|
makeptr(IOBus *bus)
|
||||||
{
|
{
|
||||||
pthread_t thread_id;
|
pthread_t thread_id;
|
||||||
|
Ptr *ptr;
|
||||||
|
|
||||||
|
ptr = malloc(sizeof(Ptr));
|
||||||
|
memset(ptr, 0, sizeof(Ptr));
|
||||||
ptr->bus = bus;
|
ptr->bus = bus;
|
||||||
bus->dev[PTR] = (Busdev){ ptr, wake_ptr, 0 };
|
bus->dev[PTR] = (Busdev){ ptr, wake_ptr, 0 };
|
||||||
pthread_create(&thread_id, nil, ptrthread, ptr);
|
pthread_create(&thread_id, nil, ptrthread, ptr);
|
||||||
|
|||||||
@@ -120,12 +120,17 @@ fail:
|
|||||||
fprintf(stderr, "couldn't open tty %s\n", path);
|
fprintf(stderr, "couldn't open tty %s\n", path);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
Tty*
|
||||||
inittty(Tty *tty, IOBus *bus)
|
maketty(IOBus *bus)
|
||||||
{
|
{
|
||||||
pthread_t thread_id;
|
pthread_t thread_id;
|
||||||
|
Tty *tty;
|
||||||
|
|
||||||
|
tty = malloc(sizeof(Tty));
|
||||||
|
memset(tty, 0, sizeof(Tty));
|
||||||
tty->fd = -1;
|
tty->fd = -1;
|
||||||
tty->bus = bus;
|
tty->bus = bus;
|
||||||
bus->dev[TTY] = (Busdev){ tty, wake_tty, 0 };
|
bus->dev[TTY] = (Busdev){ tty, wake_tty, 0 };
|
||||||
pthread_create(&thread_id, nil, ttythread, tty);
|
pthread_create(&thread_id, nil, ttythread, tty);
|
||||||
|
return tty;
|
||||||
}
|
}
|
||||||
|
|||||||
1329
misc/as6.c
1329
misc/as6.c
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user