OpenCores
URL https://opencores.org/ocsvn/eco32/eco32/trunk

Subversion Repositories eco32

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /eco32/trunk/sim
    from Rev 24 to Rev 25
    Reverse comparison

Rev 24 → Rev 25

/output.c
45,7 → 45,7
/* output device not installed */
return;
}
cPrintf("Resetting output device...\n");
cPrintf("Resetting Output Device...\n");
fseek(outputFile, 0, SEEK_SET);
}
 
/dspkbd.c
1,5 → 1,5
/*
* display.c -- display controller simulation
* dspkbd.h -- display & keyboard controller simulation
*/
 
 
794,7 → 794,7
if (debug) {
cPrintf("\n**** KEYBOARD CALLBACK ****\n");
}
timerStart(KEYBOARD_MSEC, kbdCallback, dev);
timerStart(KEYBOARD_USEC, kbdCallback, dev);
if (kbdBufWritePtr == kbdBufReadPtr) {
/* no character ready */
return;
886,7 → 886,7
kbdBufInit();
kbdCtrl = 0;
kbdData = 0;
timerStart(KEYBOARD_MSEC, kbdCallback, 0);
timerStart(KEYBOARD_USEC, kbdCallback, 0);
}
 
 
/term.c
59,7 → 59,7
if (debug) {
cPrintf("\n**** TERM RCVR CALLBACK ****\n");
}
timerStart(TERM_RCVR_MSEC, rcvrCallback, dev);
timerStart(TERM_RCVR_USEC, rcvrCallback, dev);
c = fgetc(terminals[dev].in);
if (c == EOF) {
/* no character typed */
98,12 → 98,12
if (debug) {
cPrintf("\n**** TERM READ from 0x%08X", addr);
}
dev = addr >> 4;
dev = addr >> 12;
if (dev >= numTerminals) {
/* illegal device */
throwException(EXC_BUS_TIMEOUT);
}
reg = addr & 0x0F;
reg = addr & 0x0FFF;
if (reg == TERM_RCVR_CTRL) {
data = terminals[dev].rcvrCtrl;
} else
139,12 → 139,12
cPrintf("\n**** TERM WRITE to 0x%08X, data = 0x%08X ****\n",
addr, data);
}
dev = addr >> 4;
dev = addr >> 12;
if (dev >= numTerminals) {
/* illegal device */
throwException(EXC_BUS_TIMEOUT);
}
reg = addr & 0x0F;
reg = addr & 0x0FFF;
if (reg == TERM_RCVR_CTRL) {
if (data & TERM_RCVR_IEN) {
terminals[dev].rcvrCtrl |= TERM_RCVR_IEN;
196,7 → 196,7
/* lower terminal xmtr interrupt */
cpuResetInterrupt(terminals[dev].xmtrIRQ);
}
timerStart(TERM_XMTR_MSEC, xmtrCallback, dev);
timerStart(TERM_XMTR_USEC, xmtrCallback, dev);
} else {
/* illegal register */
throwException(EXC_BUS_TIMEOUT);
215,7 → 215,7
terminals[i].rcvrCtrl = 0;
terminals[i].rcvrData = 0;
terminals[i].rcvrIRQ = IRQ_TERM_0_RCVR + 2 * i;
timerStart(TERM_RCVR_MSEC, rcvrCallback, i);
timerStart(TERM_RCVR_USEC, rcvrCallback, i);
terminals[i].xmtrCtrl = TERM_XMTR_RDY;
terminals[i].xmtrData = 0;
terminals[i].xmtrIRQ = IRQ_TERM_0_XMTR + 2 * i;
/dspkbd.h
20,7 → 20,7
 
#define KEYBOARD_RDY 0x01 /* keyboard has a character */
#define KEYBOARD_IEN 0x02 /* enable keyboard interrupt */
#define KEYBOARD_MSEC 20 /* input checking interval */
#define KEYBOARD_USEC 2000 /* input checking interval */
 
 
Word keyboardRead(Word addr);
/term.h
14,11 → 14,11
 
#define TERM_RCVR_RDY 0x01 /* receiver has a character */
#define TERM_RCVR_IEN 0x02 /* enable receiver interrupt */
#define TERM_RCVR_MSEC 20 /* input checking interval */
#define TERM_RCVR_USEC 2000 /* input checking interval */
 
#define TERM_XMTR_RDY 0x01 /* transmitter accepts a character */
#define TERM_XMTR_IEN 0x02 /* enable transmitter interrupt */
#define TERM_XMTR_MSEC 8 /* output speed */
#define TERM_XMTR_USEC 1042 /* output speed */
 
 
Word termRead(Word addr);
/cpu.c
42,7 → 42,6
static Word psw; /* processor status word */
static Word r[32]; /* general purpose registers */
 
static int instrCount; /* counts instrs for timer tick */
static unsigned irqPending; /* one bit for each pending IRQ */
 
static Bool breakSet; /* breakpoint set if true */
59,15 → 58,6
/**************************************************************/
 
 
static void handleRealTimeTasks(void) {
/* handle 'real-time' tasks */
if (++instrCount == INSTRS_PER_MSEC) {
instrCount = 0;
timerTick();
}
}
 
 
static void handleInterrupts(void) {
unsigned irqMask;
unsigned irqSeen;
572,7 → 562,7
if (exception == 0) {
/* initialization */
pushEnvironment(&myEnvironment);
handleRealTimeTasks();
timerTick();
execNextInstruction();
handleInterrupts();
} else {
602,7 → 592,7
}
}
while (run) {
handleRealTimeTasks();
timerTick();
execNextInstruction();
handleInterrupts();
if (breakSet && pc == breakAddr) {
641,7 → 631,6
r[0] = 0;
psw = 0;
/* reset simulator control variables */
instrCount = 0;
irqPending = 0;
total = 0;
}
/error.c
19,6 → 19,7
#include "term.h"
#include "disk.h"
#include "output.h"
#include "shutdown.h"
#include "graph.h"
 
 
34,6 → 35,7
termExit();
diskExit();
outputExit();
shutdownExit();
graphExit();
cExit();
va_start(ap, fmt);
/disk.c
158,7 → 158,7
if (delta > diskCap) {
delta = diskCap;
}
timerStart(DISK_DELAY + (delta * DISK_SEEK) / diskCap,
timerStart(DISK_DELAY_USEC + (delta * DISK_SEEK_USEC) / diskCap,
diskCallback, 1);
}
} else {
213,7 → 213,7
if (totalSectors != 0) {
cPrintf("Disk of size %ld sectors (%ld bytes) installed.\n",
totalSectors, totalSectors * SECTOR_SIZE);
timerStart(DISK_STARTUP, diskCallback, 0);
timerStart(DISK_START_USEC, diskCallback, 0);
}
}
 
/cpu.h
7,7 → 7,8
#define _CPU_H_
 
 
#define IRQ_TIMER 14 /* timer interrupt */
#define IRQ_TIMER_1 15 /* timer 1 interrupt */
#define IRQ_TIMER_0 14 /* timer 0 interrupt */
#define IRQ_DISK 8 /* disk interrupt */
#define IRQ_KEYBOARD 4 /* keyboard interrupt */
#define IRQ_TERM_1_RCVR 3 /* terminal 1 receiver interrupt */
/Makefile
11,7 → 11,8
 
SRCS = main.c console.c error.c except.c command.c \
instr.c asm.c disasm.c cpu.c mmu.c memory.c \
timer.c dspkbd.c term.c disk.c output.c graph.c
timer.c dspkbd.c term.c disk.c output.c shutdown.c \
graph.c
OBJS = $(patsubst %.c,%.o,$(SRCS))
BIN = sim
 
/disk.h
21,9 → 21,9
#define DISK_DONE 0x10 /* 1 = disk has finished the command */
#define DISK_READY 0x20 /* 1 = capacity valid, disk accepts command */
 
#define DISK_DELAY 10 /* seek start/settle + rotational delay */
#define DISK_SEEK 50 /* full disk seek time */
#define DISK_STARTUP 1000 /* disk startup time (until DISK_READY) */
#define DISK_DELAY_USEC 10000 /* seek start/settle + rotational delay */
#define DISK_SEEK_USEC 50000 /* full disk seek time */
#define DISK_START_USEC 1000000 /* disk startup time (until DISK_READY) */
 
 
Word diskRead(Word addr);
/memory.c
19,6 → 19,7
#include "term.h"
#include "disk.h"
#include "output.h"
#include "shutdown.h"
#include "graph.h"
 
 
73,6 → 74,10
data = outputRead(pAddr & IO_REG_MASK);
return data;
}
if ((pAddr & IO_DEV_MASK) == SHUTDOWN_BASE) {
data = shutdownRead(pAddr & IO_REG_MASK);
return data;
}
if ((pAddr & IO_DEV_MASK) >= GRAPH_BASE) {
data = graphRead(pAddr & IO_GRAPH_MASK);
return data;
159,6 → 164,10
outputWrite(pAddr & IO_REG_MASK, data);
return;
}
if ((pAddr & IO_DEV_MASK) == SHUTDOWN_BASE) {
shutdownWrite(pAddr & IO_REG_MASK, data);
return;
}
if ((pAddr & IO_DEV_MASK) >= GRAPH_BASE) {
graphWrite(pAddr & IO_GRAPH_MASK, data);
return;
/shutdown.c
0,0 → 1,61
/*
* shutdown.c -- shutdown device
*/
 
 
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
 
#include "common.h"
#include "console.h"
#include "error.h"
#include "cpu.h"
#include "mmu.h"
#include "memory.h"
#include "timer.h"
#include "dspkbd.h"
#include "term.h"
#include "disk.h"
#include "output.h"
#include "shutdown.h"
#include "graph.h"
 
 
Word shutdownRead(Word addr) {
/* the shutdown device always returns 0 on read */
return 0;
}
 
 
void shutdownWrite(Word addr, Word data) {
/* the device supports a single function: exiting the simulator */
cpuExit();
mmuExit();
memoryExit();
timerExit();
displayExit();
keyboardExit();
termExit();
diskExit();
outputExit();
shutdownExit();
graphExit();
cPrintf("ECO32 Simulator shutdown\n");
cExit();
exit(data & 0xFF);
}
 
 
void shutdownReset(void) {
cPrintf("Resetting Shutdown Device...\n");
}
 
 
void shutdownInit(void) {
shutdownReset();
}
 
 
void shutdownExit(void) {
}
/command.c
22,6 → 22,8
#include "dspkbd.h"
#include "term.h"
#include "disk.h"
#include "output.h"
#include "shutdown.h"
#include "graph.h"
 
 
731,6 → 733,8
keyboardReset();
termReset();
diskReset();
outputReset();
shutdownReset();
graphReset();
memoryReset();
mmuReset();
/timer.c
19,6 → 19,9
#define TIME_WRAP 1000000 /* avoid overflow of current time */
 
 
/*
* data structure for simulation timer
*/
typedef struct timer {
struct timer *next;
int alarm;
27,29 → 30,47
} Timer;
 
 
/*
* data structure for timer/counter device
*/
typedef struct {
Word ctrl;
Word divisor;
Word counter;
int irq;
} TimerCounter;
 
 
static Bool debug = false;
 
static Timer *activeTimers = NULL;
static Timer *freeTimers = NULL;
static int currentTime = 0; /* measured in clock cycles */
 
static int currentTime = 0;
static TimerCounter timerCounters[NUMBER_TMRCNT];
 
static Word timerCtrl = 0x00000000;
static Word timerDivisor = 0xFFFFFFFF;
static Word timerCounter = 0xFFFFFFFF;
 
 
Word timerRead(Word addr) {
int dev, reg;
Word data;
 
if (debug) {
cPrintf("\n**** TIMER READ from 0x%08X", addr);
}
if (addr == TIMER_CTRL) {
data = timerCtrl;
dev = addr >> 12;
if (dev >= NUMBER_TMRCNT) {
/* illegal device */
throwException(EXC_BUS_TIMEOUT);
}
reg = addr & 0x0FFF;
if (reg == TIMER_CTRL) {
data = timerCounters[dev].ctrl;
} else
if (addr == TIMER_DIVISOR) {
data = timerDivisor;
if (reg == TIMER_DIVISOR) {
data = timerCounters[dev].divisor;
} else
if (reg == TIMER_COUNTER) {
data = timerCounters[dev].counter;
} else {
/* illegal register */
throwException(EXC_BUS_TIMEOUT);
62,33 → 83,41
 
 
void timerWrite(Word addr, Word data) {
int dev, reg;
 
if (debug) {
cPrintf("\n**** TIMER WRITE to 0x%08X, data = 0x%08X ****\n",
addr, data);
}
if (addr == TIMER_CTRL) {
dev = addr >> 12;
if (dev >= NUMBER_TMRCNT) {
/* illegal device */
throwException(EXC_BUS_TIMEOUT);
}
reg = addr & 0x0FFF;
if (reg == TIMER_CTRL) {
if (data & TIMER_IEN) {
timerCtrl |= TIMER_IEN;
timerCounters[dev].ctrl |= TIMER_IEN;
} else {
timerCtrl &= ~TIMER_IEN;
timerCounters[dev].ctrl &= ~TIMER_IEN;
}
if (data & TIMER_EXP) {
timerCtrl |= TIMER_EXP;
timerCounters[dev].ctrl |= TIMER_EXP;
} else {
timerCtrl &= ~TIMER_EXP;
timerCounters[dev].ctrl &= ~TIMER_EXP;
}
if ((timerCtrl & TIMER_IEN) != 0 &&
(timerCtrl & TIMER_EXP) != 0) {
if ((timerCounters[dev].ctrl & TIMER_IEN) != 0 &&
(timerCounters[dev].ctrl & TIMER_EXP) != 0) {
/* raise timer interrupt */
cpuSetInterrupt(IRQ_TIMER);
cpuSetInterrupt(timerCounters[dev].irq);
} else {
/* lower timer interrupt */
cpuResetInterrupt(IRQ_TIMER);
cpuResetInterrupt(timerCounters[dev].irq);
}
} else
if (addr == TIMER_DIVISOR) {
timerDivisor = data;
timerCounter = data;
if (reg == TIMER_DIVISOR) {
timerCounters[dev].divisor = data;
timerCounters[dev].counter = data;
} else {
/* illegal register */
throwException(EXC_BUS_TIMEOUT);
100,9 → 129,12
Timer *timer;
void (*callback)(int param);
int param;
int i;
 
/* increment current time, avoid overflow */
if (++currentTime == TIME_WRAP) {
/* increment current time */
currentTime += CC_PER_INSTR;
/* avoid overflow */
if (currentTime >= TIME_WRAP) {
currentTime -= TIME_WRAP;
timer = activeTimers;
while (timer != NULL) {
121,19 → 153,23
freeTimers = timer;
(*callback)(param);
}
/* decrement counter and check if an interrupt must be raised */
if (--timerCounter == 0) {
timerCounter = timerDivisor;
timerCtrl |= TIMER_EXP;
if (timerCtrl & TIMER_IEN) {
/* raise timer interrupt */
cpuSetInterrupt(IRQ_TIMER);
/* decrement counters and check if an interrupt must be raised */
for (i = 0; i < NUMBER_TMRCNT; i++) {
if (timerCounters[i].counter <= CC_PER_INSTR) {
timerCounters[i].counter += timerCounters[i].divisor - CC_PER_INSTR;
timerCounters[i].ctrl |= TIMER_EXP;
if (timerCounters[i].ctrl & TIMER_IEN) {
/* raise timer interrupt */
cpuSetInterrupt(timerCounters[i].irq);
}
} else {
timerCounters[i].counter -= CC_PER_INSTR;
}
}
}
 
 
void timerStart(int msec, void (*callback)(int param), int param) {
void timerStart(int usec, void (*callback)(int param), int param) {
Timer *timer;
Timer *p;
 
142,7 → 178,7
}
timer = freeTimers;
freeTimers = timer->next;
timer->alarm = currentTime + msec;
timer->alarm = currentTime + usec * CC_PER_USEC;
timer->callback = callback;
timer->param = param;
if (activeTimers == NULL ||
165,6 → 201,7
 
void timerReset(void) {
Timer *timer;
int i;
 
cPrintf("Resetting Timer...\n");
while (activeTimers != NULL) {
173,6 → 210,12
timer->next = freeTimers;
freeTimers = timer;
}
for (i = 0; i < NUMBER_TMRCNT; i++) {
timerCounters[i].ctrl = 0x00000000;
timerCounters[i].divisor = 0xFFFFFFFF;
timerCounters[i].counter = 0xFFFFFFFF;
timerCounters[i].irq = IRQ_TIMER_0 + i;
}
}
 
 
195,7 → 238,12
void timerExit(void) {
Timer *timer;
 
timerReset();
while (activeTimers != NULL) {
timer = activeTimers;
activeTimers = timer->next;
timer->next = freeTimers;
freeTimers = timer;
}
while (freeTimers != NULL) {
timer = freeTimers;
freeTimers = timer->next;
/shutdown.h
0,0 → 1,18
/*
* shutdown.h -- shutdown device
*/
 
 
#ifndef _SHUTDOWN_H_
#define _SHUTDOWN_H_
 
 
Word shutdownRead(Word addr);
void shutdownWrite(Word addr, Word data);
 
void shutdownReset(void);
void shutdownInit(void);
void shutdownExit(void);
 
 
#endif /* _SHUTDOWN_H_ */
/main.c
20,6 → 20,7
#include "term.h"
#include "disk.h"
#include "output.h"
#include "shutdown.h"
#include "graph.h"
 
 
150,6 → 151,7
termInit(numTerms);
diskInit(diskName);
outputInit(outputName);
shutdownInit();
if (graphics) {
graphInit();
}
186,6 → 188,7
termExit();
diskExit();
outputExit();
shutdownExit();
graphExit();
cPrintf("ECO32 Simulator finished\n");
cExit();
/timer.h
9,11 → 9,13
 
#define TIMER_CTRL 0 /* timer control register */
#define TIMER_DIVISOR 4 /* timer divisor register */
#define TIMER_COUNTER 8 /* timer counter register */
 
#define TIMER_EXP 0x01 /* timer has expired */
#define TIMER_IEN 0x02 /* enable timer interrupt */
 
#define NUMBER_TIMERS 20 /* total number of simulation timers */
#define NUMBER_TIMERS 20 /* number of simulation timers */
#define NUMBER_TMRCNT 2 /* number of timer/counters */
 
 
Word timerRead(Word addr);
20,7 → 22,7
void timerWrite(Word addr, Word data);
 
void timerTick(void);
void timerStart(int msec, void (*callback)(int param), int param);
void timerStart(int usec, void (*callback)(int param), int param);
 
void timerReset(void);
void timerInit(void);
/common.h
30,6 → 30,7
#define MAX_NTERMS 2 /* max number of terminals */
#define DISK_BASE 0x30400000 /* physical disk base address */
#define OUTPUT_BASE 0x3F000000 /* physical output device address */
#define SHUTDOWN_BASE 0x3F100000 /* physical shutdown device address */
#define GRAPH_BASE 0x3FC00000 /* physical grahics base address */
/* extends to end of address space */
 
37,7 → 38,8
#define OFFSET_MASK (PAGE_SIZE - 1) /* mask for offset within a page */
#define PAGE_MASK (~OFFSET_MASK) /* mask for page number */
 
#define INSTRS_PER_MSEC 1700 /* average execution speed */
#define CC_PER_USEC 50 /* clock cycles per microsecond */
#define CC_PER_INSTR 18 /* clock cycles per instruction */
 
 
typedef enum { false, true } Bool; /* truth values */

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.