URL
https://opencores.org/ocsvn/eco32/eco32/trunk
Subversion Repositories eco32
Compare Revisions
- This comparison shows the changes necessary to convert path
/eco32/trunk
- from Rev 15 to Rev 16
- ↔ Reverse comparison
Rev 15 → Rev 16
/monitor/monitor-digilent/mmu.c
0,0 → 1,104
/* |
* mmu.c -- memory and TLB access |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "mmu.h" |
#include "start.h" |
|
|
static Word tlbIndex; |
static Word tlbEntryHi; |
static Word tlbEntryLo; |
|
|
Word mmuReadWord(Word vAddr) { |
return *(Word *)vAddr; |
} |
|
|
Half mmuReadHalf(Word vAddr) { |
return *(Half *)vAddr; |
} |
|
|
Byte mmuReadByte(Word vAddr) { |
return *(Byte *)vAddr; |
} |
|
|
void mmuWriteWord(Word vAddr, Word data) { |
*(Word *)vAddr = data; |
} |
|
|
void mmuWriteHalf(Word vAddr, Half data) { |
*(Half *)vAddr = data; |
} |
|
|
void mmuWriteByte(Word vAddr, Byte data) { |
*(Byte *)vAddr = data; |
} |
|
|
Word mmuGetIndex(void) { |
return tlbIndex; |
} |
|
|
void mmuSetIndex(Word value) { |
tlbIndex = value; |
} |
|
|
Word mmuGetEntryHi(void) { |
return tlbEntryHi; |
} |
|
|
void mmuSetEntryHi(Word value) { |
tlbEntryHi = value; |
} |
|
|
Word mmuGetEntryLo(void) { |
return tlbEntryLo; |
} |
|
|
void mmuSetEntryLo(Word value) { |
tlbEntryLo = value; |
} |
|
|
TLB_Entry mmuGetTLB(int index) { |
Word hi; |
Word lo; |
TLB_Entry result; |
|
hi = getTLB_HI(index); |
lo = getTLB_LO(index); |
result.page = hi & PAGE_MASK; |
result.frame = lo & PAGE_MASK; |
result.write = (lo & TLB_WRITE) ? true : false; |
result.valid = (lo & TLB_VALID) ? true : false; |
return result; |
} |
|
|
void mmuSetTLB(int index, TLB_Entry tlbEntry) { |
Word flags; |
|
flags = 0; |
if (tlbEntry.write) { |
flags |= TLB_WRITE; |
} |
if (tlbEntry.valid) { |
flags |= TLB_VALID; |
} |
setTLB(index, tlbEntry.page, tlbEntry.frame | flags); |
} |
/monitor/monitor-digilent/instr.c
0,0 → 1,115
/* |
* instr.c -- instruction encoding |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "instr.h" |
|
|
/* |
* This is the ECO32 machine instruction set. |
* The table below needs no particular order |
* and may have gaps in the instruction encoding. |
*/ |
Instr instrTbl[] = { |
{ "add", FORMAT_RRY, OP_ADD }, |
{ "sub", FORMAT_RRY, OP_SUB }, |
{ "mul", FORMAT_RRY, OP_MUL }, |
{ "mulu", FORMAT_RRX, OP_MULU }, |
{ "div", FORMAT_RRY, OP_DIV }, |
{ "divu", FORMAT_RRX, OP_DIVU }, |
{ "rem", FORMAT_RRY, OP_REM }, |
{ "remu", FORMAT_RRX, OP_REMU }, |
{ "and", FORMAT_RRX, OP_AND }, |
{ "or", FORMAT_RRX, OP_OR }, |
{ "xor", FORMAT_RRX, OP_XOR }, |
{ "xnor", FORMAT_RRX, OP_XNOR }, |
{ "sll", FORMAT_RRX, OP_SLL }, |
{ "slr", FORMAT_RRX, OP_SLR }, |
{ "sar", FORMAT_RRX, OP_SAR }, |
{ "ldhi", FORMAT_RHH, OP_LDHI }, |
{ "beq", FORMAT_RRB, OP_BEQ }, |
{ "bne", FORMAT_RRB, OP_BNE }, |
{ "ble", FORMAT_RRB, OP_BLE }, |
{ "bleu", FORMAT_RRB, OP_BLEU }, |
{ "blt", FORMAT_RRB, OP_BLT }, |
{ "bltu", FORMAT_RRB, OP_BLTU }, |
{ "bge", FORMAT_RRB, OP_BGE }, |
{ "bgeu", FORMAT_RRB, OP_BGEU }, |
{ "bgt", FORMAT_RRB, OP_BGT }, |
{ "bgtu", FORMAT_RRB, OP_BGTU }, |
{ "j", FORMAT_J, OP_J }, |
{ "jr", FORMAT_JR, OP_JR }, |
{ "jal", FORMAT_J, OP_JAL }, |
{ "jalr", FORMAT_JR, OP_JALR }, |
{ "trap", FORMAT_N, OP_TRAP }, |
{ "rfx", FORMAT_N, OP_RFX }, |
{ "ldw", FORMAT_RRS, OP_LDW }, |
{ "ldh", FORMAT_RRS, OP_LDH }, |
{ "ldhu", FORMAT_RRS, OP_LDHU }, |
{ "ldb", FORMAT_RRS, OP_LDB }, |
{ "ldbu", FORMAT_RRS, OP_LDBU }, |
{ "stw", FORMAT_RRS, OP_STW }, |
{ "sth", FORMAT_RRS, OP_STH }, |
{ "stb", FORMAT_RRS, OP_STB }, |
{ "mvfs", FORMAT_RH, OP_MVFS }, |
{ "mvts", FORMAT_RH, OP_MVTS }, |
{ "tbs", FORMAT_N, OP_TBS }, |
{ "tbwr", FORMAT_N, OP_TBWR }, |
{ "tbri", FORMAT_N, OP_TBRI }, |
{ "tbwi", FORMAT_N, OP_TBWI } |
}; |
|
|
Instr *instrCodeTbl[64]; |
|
|
static int instrCompare(const void *instr1, const void *instr2) { |
return strcmp(((Instr *) instr1)->name, ((Instr *) instr2)->name); |
} |
|
|
void initInstrTable(void) { |
int i; |
|
/* first sort instruction table alphabetically */ |
qsort(instrTbl, sizeof(instrTbl)/sizeof(instrTbl[0]), |
sizeof(instrTbl[0]), instrCompare); |
/* then initialize instruction code table */ |
for (i = 0; i < 64; i++) { |
instrCodeTbl[i] = NULL; |
} |
for (i = 0; i < sizeof(instrTbl)/sizeof(instrTbl[0]); i++) { |
instrCodeTbl[instrTbl[i].opcode] = &instrTbl[i]; |
if (instrTbl[i].format == FORMAT_RRX || |
instrTbl[i].format == FORMAT_RRY) { |
/* enter the immediate variant of this instruction also */ |
instrCodeTbl[instrTbl[i].opcode + 1] = &instrTbl[i]; |
} |
} |
} |
|
|
Instr *lookupInstr(char *name) { |
int lo, hi, tst; |
int res; |
|
lo = 0; |
hi = sizeof(instrTbl) / sizeof(instrTbl[0]) - 1; |
while (lo <= hi) { |
tst = (lo + hi) / 2; |
res = strcmp(instrTbl[tst].name, name); |
if (res == 0) { |
return &instrTbl[tst]; |
} |
if (res < 0) { |
lo = tst + 1; |
} else { |
hi = tst - 1; |
} |
} |
return NULL; |
} |
/monitor/monitor-digilent/start.h
0,0 → 1,57
/* |
* start.h -- ECO32 ROM monitor startup and support routines |
*/ |
|
|
#ifndef _START_H_ |
#define _START_H_ |
|
|
typedef struct { |
Word reg[32]; /* general purpose registers */ |
Word psw; /* PSW */ |
Word tlbIndex; /* TLB index register */ |
Word tlbHi; /* TLB EntryHi register */ |
Word tlbLo; /* TLB EntryLo register */ |
} UserContext; |
|
typedef struct { |
Word r31; /* return address */ |
Word r29; /* stack pointer */ |
Word r16; /* local variable */ |
Word r17; /* local variable */ |
Word r18; /* local variable */ |
Word r19; /* local variable */ |
Word r20; /* local variable */ |
Word r21; /* local variable */ |
Word r22; /* local variable */ |
Word r23; /* local variable */ |
} MonitorState; |
|
|
int cinchk(void); |
int cin(void); |
int coutchk(void); |
void cout(char c); |
|
int sinchk(void); |
int sin(void); |
int soutchk(void); |
void sout(char c); |
|
int dskcap(int dskno); |
int dskio(int dskno, char cmd, int sct, Word addr, int nscts); |
|
Word getTLB_HI(int index); |
Word getTLB_LO(int index); |
void setTLB(int index, Word entryHi, Word entryLo); |
|
Bool saveState(MonitorState *msp); |
|
extern MonitorState *monitorReturn; |
extern UserContext userContext; |
|
void resume(void); |
|
|
#endif /* _START_H_ */ |
/monitor/monitor-digilent/mmu.h
0,0 → 1,45
/* |
* mmu.h -- memory and TLB access |
*/ |
|
|
#ifndef _MMU_H_ |
#define _MMU_H_ |
|
|
#define TLB_SHFT 5 /* log2 of number of TLB entries */ |
#define TLB_SIZE (1 << TLB_SHFT) /* total number of TLB entries */ |
#define TLB_MASK (TLB_SIZE - 1) /* mask for number of TLB entries */ |
#define TLB_FIXED 4 /* number of fixed TLB entries */ |
|
#define TLB_WRITE (1 << 1) /* write bit in EntryLo */ |
#define TLB_VALID (1 << 0) /* valid bit in EntryLo */ |
|
|
typedef struct { |
Word page; /* 20 high-order bits of virtual address */ |
Word frame; /* 20 high-order bits of physical address */ |
Bool write; /* must be true to allow writing to the page */ |
Bool valid; /* must be true for the entry to be valid */ |
} TLB_Entry; |
|
|
Word mmuReadWord(Word vAddr); |
Half mmuReadHalf(Word vAddr); |
Byte mmuReadByte(Word vAddr); |
void mmuWriteWord(Word vAddr, Word data); |
void mmuWriteHalf(Word vAddr, Half data); |
void mmuWriteByte(Word vAddr, Byte data); |
|
Word mmuGetIndex(void); |
void mmuSetIndex(Word value); |
Word mmuGetEntryHi(void); |
void mmuSetEntryHi(Word value); |
Word mmuGetEntryLo(void); |
void mmuSetEntryLo(Word Value); |
|
TLB_Entry mmuGetTLB(int index); |
void mmuSetTLB(int index, TLB_Entry tlbEntry); |
|
|
#endif /* _MMU_H_ */ |
/monitor/monitor-digilent/instr.h
0,0 → 1,125
/* |
* instr.h -- instruction encoding |
*/ |
|
|
#ifndef _INSTR_H_ |
#define _INSTR_H_ |
|
|
#define FORMAT_N 0 /* no operands */ |
#define FORMAT_RH 1 /* one register and a half operand */ |
#define FORMAT_RHH 2 /* one register and a half operand */ |
/* ATTENTION: high-order 16 bits encoded */ |
#define FORMAT_RRH 3 /* two registers and a half operand */ |
#define FORMAT_RRS 4 /* two registers and a signed half operand */ |
#define FORMAT_RRR 5 /* three register operands */ |
#define FORMAT_RRX 6 /* either FORMAT_RRR or FORMAT_RRH */ |
#define FORMAT_RRY 7 /* either FORMAT_RRR or FORMAT_RRS */ |
#define FORMAT_RRB 8 /* two registers and a 16 bit signed |
offset operand */ |
#define FORMAT_J 9 /* no registers and a 26 bit signed |
offset operand */ |
#define FORMAT_JR 10 /* one register operand */ |
|
|
#define MASK(n) ((((Word) 1) << n) - 1) |
#define SIGN(n) (((Word) 1) << (n - 1)) |
#define ZEXT16(x) (((Word) (x)) & MASK(16)) |
#define SEXT16(x) (((Word) (x)) & SIGN(16) ? \ |
(((Word) (x)) | ~MASK(16)) : \ |
(((Word) (x)) & MASK(16))) |
#define SEXT26(x) (((Word) (x)) & SIGN(26) ? \ |
(((Word) (x)) | ~MASK(26)) : \ |
(((Word) (x)) & MASK(26))) |
|
|
#define OP_ADD 0x00 |
#define OP_ADDI 0x01 |
#define OP_SUB 0x02 |
#define OP_SUBI 0x03 |
|
#define OP_MUL 0x04 |
#define OP_MULI 0x05 |
#define OP_MULU 0x06 |
#define OP_MULUI 0x07 |
#define OP_DIV 0x08 |
#define OP_DIVI 0x09 |
#define OP_DIVU 0x0A |
#define OP_DIVUI 0x0B |
#define OP_REM 0x0C |
#define OP_REMI 0x0D |
#define OP_REMU 0x0E |
#define OP_REMUI 0x0F |
|
#define OP_AND 0x10 |
#define OP_ANDI 0x11 |
#define OP_OR 0x12 |
#define OP_ORI 0x13 |
#define OP_XOR 0x14 |
#define OP_XORI 0x15 |
#define OP_XNOR 0x16 |
#define OP_XNORI 0x17 |
|
#define OP_SLL 0x18 |
#define OP_SLLI 0x19 |
#define OP_SLR 0x1A |
#define OP_SLRI 0x1B |
#define OP_SAR 0x1C |
#define OP_SARI 0x1D |
|
#define OP_LDHI 0x1F |
|
#define OP_BEQ 0x20 |
#define OP_BNE 0x21 |
#define OP_BLE 0x22 |
#define OP_BLEU 0x23 |
#define OP_BLT 0x24 |
#define OP_BLTU 0x25 |
#define OP_BGE 0x26 |
#define OP_BGEU 0x27 |
#define OP_BGT 0x28 |
#define OP_BGTU 0x29 |
|
#define OP_J 0x2A |
#define OP_JR 0x2B |
#define OP_JAL 0x2C |
#define OP_JALR 0x2D |
|
#define OP_TRAP 0x2E |
#define OP_RFX 0x2F |
|
#define OP_LDW 0x30 |
#define OP_LDH 0x31 |
#define OP_LDHU 0x32 |
#define OP_LDB 0x33 |
#define OP_LDBU 0x34 |
|
#define OP_STW 0x35 |
#define OP_STH 0x36 |
#define OP_STB 0x37 |
|
#define OP_MVFS 0x38 |
#define OP_MVTS 0x39 |
#define OP_TBS 0x3A |
#define OP_TBWR 0x3B |
#define OP_TBRI 0x3C |
#define OP_TBWI 0x3D |
|
|
typedef struct { |
char *name; |
int format; |
Byte opcode; |
} Instr; |
|
|
extern Instr instrTbl[]; |
extern Instr *instrCodeTbl[]; |
|
|
void initInstrTable(void); |
Instr *lookupInstr(char *name); |
|
|
#endif /* _INSTR_H_ */ |
/monitor/monitor-digilent/start.s
0,0 → 1,389
; |
; start.s -- ECO32 ROM monitor startup and support routines |
; |
|
.set dmapaddr,0xC0000000 ; base of directly mapped addresses |
.set stacktop,0xC4000000 ; monitor stack is at top of memory |
|
.set PSW,0 ; reg # of PSW |
.set TLB_INDEX,1 ; reg # of TLB Index |
.set TLB_ENTRY_HI,2 ; reg # of TLB EntryHi |
.set TLB_ENTRY_LO,3 ; reg # of TLB EntryLo |
.set TLB_ENTRIES,32 ; number of TLB entries |
|
.set USER_CONTEXT_SIZE,36*4 ; size of user context |
|
;*************************************************************** |
|
.import _ecode |
.import _edata |
.import _ebss |
|
.import kbdinit |
.import kbdinchk |
.import kbdin |
|
.import dspinit |
.import dspoutchk |
.import dspout |
|
.import serinit |
.import ser0inchk |
.import ser0in |
.import ser0outchk |
.import ser0out |
|
.import sctcapctl |
.import sctioctl |
.import sctcapser |
.import sctioser |
|
.import main |
|
.export _bcode |
.export _bdata |
.export _bbss |
|
.export cinchk |
.export cin |
.export coutchk |
.export cout |
.export sinchk |
.export sin |
.export soutchk |
.export sout |
.export dskcap |
.export dskio |
|
.export getTLB_HI |
.export getTLB_LO |
.export setTLB |
|
.export saveState |
.export monitorReturn |
|
.import userContext |
.export resume |
|
;*************************************************************** |
|
.code |
_bcode: |
|
.data |
_bdata: |
|
.bss |
_bbss: |
|
;*************************************************************** |
|
.code |
.align 4 |
|
reset: |
j start |
|
interrupt: |
j isr |
|
userMiss: |
j umsr |
|
;*************************************************************** |
|
.code |
.align 4 |
|
cinchk: |
j kbdinchk |
; j ser0inchk |
|
cin: |
j kbdin |
; j ser0in |
|
coutchk: |
j dspoutchk |
; j ser0outchk |
|
cout: |
j dspout |
; j ser0out |
|
sinchk: |
j ser0inchk |
|
sin: |
j ser0in |
|
soutchk: |
j ser0outchk |
|
sout: |
j ser0out |
|
dskcap: |
j dcap |
|
dskio: |
j dio |
|
;*************************************************************** |
|
.code |
.align 4 |
|
start: |
; force CPU into a defined state |
mvts $0,PSW ; disable interrupts and user mode |
|
; initialize TLB |
mvts $0,TLB_ENTRY_LO ; invalidate all TLB entries |
add $8,$0,dmapaddr ; by impossible virtual page number |
add $9,$0,$0 |
add $10,$0,TLB_ENTRIES |
tlbloop: |
mvts $8,TLB_ENTRY_HI |
mvts $9,TLB_INDEX |
tbwi |
add $8,$8,0x1000 ; all entries must be different |
add $9,$9,1 |
bne $9,$10,tlbloop |
|
; copy data segment |
add $10,$0,_bdata ; lowest dst addr to be written to |
add $8,$0,_edata ; one above the top dst addr |
sub $9,$8,$10 ; $9 = size of data segment |
add $9,$9,_ecode ; data is waiting right after code |
j cpytest |
cpyloop: |
ldw $11,$9,0 ; src addr in $9 |
stw $11,$8,0 ; dst addr in $8 |
cpytest: |
sub $8,$8,4 ; downward |
sub $9,$9,4 |
bgeu $8,$10,cpyloop |
|
; clear bss segment |
add $8,$0,_bbss ; start with first word of bss |
add $9,$0,_ebss ; this is one above the top |
j clrtest |
clrloop: |
stw $0,$8,0 ; dst addr in $8 |
add $8,$8,4 ; upward |
clrtest: |
bltu $8,$9,clrloop |
|
; now do some useful work |
add $29,$0,stacktop ; setup monitor stack |
jal dspinit ; init display |
jal kbdinit ; init keyboard |
jal serinit ; init serial interface |
jal main ; enter command loop |
|
; main should never return |
j start ; just to be sure... |
|
;*************************************************************** |
|
; Word getTLB_HI(int index) |
getTLB_HI: |
mvts $4,TLB_INDEX |
tbri |
mvfs $2,TLB_ENTRY_HI |
jr $31 |
|
; Word getTLB_LO(int index) |
getTLB_LO: |
mvts $4,TLB_INDEX |
tbri |
mvfs $2,TLB_ENTRY_LO |
jr $31 |
|
; void setTLB(int index, Word entryHi, Word entryLo) |
setTLB: |
mvts $4,TLB_INDEX |
mvts $5,TLB_ENTRY_HI |
mvts $6,TLB_ENTRY_LO |
tbwi |
jr $31 |
|
;*************************************************************** |
|
; int dskcap(int dskno) |
dcap: |
bne $4,$0,dcapser |
j sctcapctl |
dcapser: |
j sctcapser |
|
; int dskio(int dskno, char cmd, int sct, Word addr, int nscts) |
dio: |
bne $4,$0,dioser |
add $4,$5,$0 |
add $5,$6,$0 |
add $6,$7,$0 |
ldw $7,$29,16 |
j sctioctl |
dioser: |
add $4,$5,$0 |
add $5,$6,$0 |
add $6,$7,$0 |
ldw $7,$29,16 |
j sctioser |
|
;*************************************************************** |
|
.code |
.align 4 |
|
; Bool saveState(MonitorState *msp) |
; always return 'true' here |
saveState: |
stw $31,$4,0*4 ; return address |
stw $29,$4,1*4 ; stack pointer |
stw $16,$4,2*4 ; local variables |
stw $17,$4,3*4 |
stw $18,$4,4*4 |
stw $19,$4,5*4 |
stw $20,$4,6*4 |
stw $21,$4,7*4 |
stw $22,$4,8*4 |
stw $23,$4,9*4 |
add $2,$0,1 |
jr $31 |
|
; load state when re-entering monitor |
; this appears as if returning from saveState |
; but the return value is 'false' here |
loadState: |
ldw $8,$0,monitorReturn |
beq $8,$0,loadState ; fatal error: monitor state lost |
ldw $31,$8,0*4 ; return address |
ldw $29,$8,1*4 ; stack pointer |
ldw $16,$8,2*4 ; local variables |
ldw $17,$8,3*4 |
ldw $18,$8,4*4 |
ldw $19,$8,5*4 |
ldw $20,$8,6*4 |
ldw $21,$8,7*4 |
ldw $22,$8,8*4 |
ldw $23,$8,9*4 |
add $2,$0,0 |
jr $31 |
|
.bss |
.align 4 |
|
; extern MonitorState *monitorReturn |
monitorReturn: |
.space 4 |
|
; extern UserContext userContext |
userContext: |
.space USER_CONTEXT_SIZE |
|
;*************************************************************** |
|
.code |
.align 4 |
|
; void resume(void) |
; use userContext to load state |
resume: |
mvts $0,PSW |
add $28,$0,userContext |
.nosyn |
ldw $8,$28,33*4 ; tlbIndex |
mvts $8,TLB_INDEX |
ldw $8,$28,34*4 ; tlbWntryHi |
mvts $8,TLB_ENTRY_HI |
ldw $8,$28,35*4 ; tlbEntryLo |
mvts $8,TLB_ENTRY_LO |
;ldw $0,$28,0*4 ; registers |
ldw $1,$28,1*4 |
ldw $2,$28,2*4 |
ldw $3,$28,3*4 |
ldw $4,$28,4*4 |
ldw $5,$28,5*4 |
ldw $6,$28,6*4 |
ldw $7,$28,7*4 |
ldw $8,$28,8*4 |
ldw $9,$28,9*4 |
ldw $10,$28,10*4 |
ldw $11,$28,11*4 |
ldw $12,$28,12*4 |
ldw $13,$28,13*4 |
ldw $14,$28,14*4 |
ldw $15,$28,15*4 |
ldw $16,$28,16*4 |
ldw $17,$28,17*4 |
ldw $18,$28,18*4 |
ldw $19,$28,19*4 |
ldw $20,$28,20*4 |
ldw $21,$28,21*4 |
ldw $22,$28,22*4 |
ldw $23,$28,23*4 |
ldw $24,$28,24*4 |
ldw $25,$28,25*4 |
ldw $26,$28,26*4 |
ldw $27,$28,27*4 |
;ldw $28,$28,28*4 |
ldw $29,$28,29*4 |
ldw $30,$28,30*4 |
ldw $31,$28,31*4 |
ldw $28,$28,32*4 ; psw |
mvts $28,PSW |
rfx |
.syn |
|
; interrupt entry |
; use userContext to store state |
isr: |
umsr: |
.nosyn |
ldhi $28,userContext |
or $28,$28,userContext |
stw $0,$28,0*4 ; registers |
stw $1,$28,1*4 |
stw $2,$28,2*4 |
stw $3,$28,3*4 |
stw $4,$28,4*4 |
stw $5,$28,5*4 |
stw $6,$28,6*4 |
stw $7,$28,7*4 |
stw $8,$28,8*4 |
stw $9,$28,9*4 |
stw $10,$28,10*4 |
stw $11,$28,11*4 |
stw $12,$28,12*4 |
stw $13,$28,13*4 |
stw $14,$28,14*4 |
stw $15,$28,15*4 |
stw $16,$28,16*4 |
stw $17,$28,17*4 |
stw $18,$28,18*4 |
stw $19,$28,19*4 |
stw $20,$28,20*4 |
stw $21,$28,21*4 |
stw $22,$28,22*4 |
stw $23,$28,23*4 |
stw $24,$28,24*4 |
stw $25,$28,25*4 |
stw $26,$28,26*4 |
stw $27,$28,27*4 |
stw $28,$28,28*4 |
stw $29,$28,29*4 |
stw $30,$28,30*4 |
stw $31,$28,31*4 |
mvfs $8,PSW |
stw $8,$28,32*4 ; psw |
mvfs $8,TLB_INDEX |
stw $8,$28,33*4 ; tlbIndex |
mvfs $8,TLB_ENTRY_HI |
stw $8,$28,34*4 ; tlbEntryHi |
mvfs $8,TLB_ENTRY_LO |
stw $8,$28,35*4 ; tlbEntryLo |
.syn |
j loadState |
/monitor/monitor-digilent/load.c
0,0 → 1,223
/* |
* load.c -- load S-record file from serial line |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "load.h" |
#include "serial.h" |
#include "cpu.h" |
#include "mmu.h" |
|
|
#define NUM_TRIES 10 |
#define WAIT_DELAY 350000 |
|
#define SYN ((unsigned char) 's') |
#define ACK ((unsigned char) 'a') |
|
#define LINE_SIZE 520 |
|
|
static Byte line[LINE_SIZE]; |
|
|
static Word getByte(int index) { |
Word hi, lo; |
|
hi = line[index + 0]; |
if (hi >= '0' && hi <= '9') { |
hi -= '0'; |
} else |
if (hi >= 'A' && hi <= 'F') { |
hi -= 'A' - 10; |
} else |
if (hi >= 'a' && hi <= 'f') { |
hi -= 'a' - 10; |
} else { |
return -1; |
} |
lo = line[index + 1]; |
if (lo >= '0' && lo <= '9') { |
lo -= '0'; |
} else |
if (lo >= 'A' && lo <= 'F') { |
lo -= 'A' - 10; |
} else |
if (lo >= 'a' && lo <= 'f') { |
lo -= 'a' - 10; |
} else { |
return -1; |
} |
return (hi << 4) | lo; |
} |
|
|
static void serialOut(int serno, Word c) { |
if (serno == 0) { |
ser0out(c); |
} else { |
ser1out(c); |
} |
} |
|
|
static int serialChk(int serno) { |
if (serno == 0) { |
return ser0inchk(); |
} else { |
return ser1inchk(); |
} |
} |
|
|
static Word serialIn(int serno) { |
if (serno == 0) { |
return ser0in(); |
} else { |
return ser1in(); |
} |
} |
|
|
void load(int serno) { |
int i, j; |
Bool run; |
int type; |
int count; |
Word chksum; |
Word addr; |
Byte b; |
|
printf("Trying to connect to load server...\n"); |
for (i = 0; i < NUM_TRIES; i++) { |
serialOut(serno, SYN); |
for (j = 0; j < WAIT_DELAY; j++) { |
if (serialChk(serno) != 0) { |
break; |
} |
} |
if (j < WAIT_DELAY) { |
break; |
} |
printf("Request timed out...\n"); |
} |
if (i == NUM_TRIES || |
serialIn(serno) != ACK) { |
printf("Unable to establish connection to load server.\n"); |
return; |
} |
serialOut(serno, ACK); |
printf("Connected to load server.\n"); |
run = true; |
while (run) { |
serialOut(serno, 'r'); |
for (i = 0; i < LINE_SIZE; i++) { |
line[i] = serialIn(serno); |
if (line[i] == '\n') { |
break; |
} |
} |
if (i == LINE_SIZE) { |
printf("Error: too many characters in S-record!\n"); |
break; |
} |
line[i] = '\0'; |
printf("%s\n", line); |
if (line[0] != 'S') { |
printf("Error: malformed S-record!\n"); |
break; |
} |
type = line[1]; |
count = getByte(2); |
if (i != 2 * count + 4) { |
printf("Error: inconsistent byte count in S-record!\n"); |
break; |
} |
chksum = 0; |
for (j = 2; j < i; j += 2) { |
chksum += getByte(j); |
} |
if ((chksum & 0xFF) != 0xFF) { |
printf("Error: wrong checksum in S-record!\n"); |
break; |
} |
switch (type) { |
case '0': |
/* S0 record: header (skip) */ |
break; |
case '1': |
/* S1 record: 2 byte load address + data (load data) */ |
addr = (getByte( 4) << 8) | |
(getByte( 6) << 0); |
addr |= 0xC0000000; |
for (j = 0; j < count - 3; j++) { |
b = getByte(2 * j + 8); |
mmuWriteByte(addr + j, b); |
} |
break; |
case '2': |
/* S2 record: 3 byte load address + data (load data) */ |
addr = (getByte( 4) << 16) | |
(getByte( 6) << 8) | |
(getByte( 8) << 0); |
addr |= 0xC0000000; |
for (j = 0; j < count - 4; j++) { |
b = getByte(2 * j + 10); |
mmuWriteByte(addr + j, b); |
} |
break; |
case '3': |
/* S3 record: 4 byte load address + data (load data) */ |
addr = (getByte( 4) << 24) | |
(getByte( 6) << 26) | |
(getByte( 8) << 8) | |
(getByte(10) << 0); |
addr |= 0xC0000000; |
for (j = 0; j < count - 5; j++) { |
b = getByte(2 * j + 12); |
mmuWriteByte(addr + j, b); |
} |
break; |
case '5': |
/* S5 record: record count (skip) */ |
break; |
case '7': |
/* S7 record: 4 byte start address (set PC, stop loading) */ |
addr = (getByte( 4) << 24) | |
(getByte( 6) << 26) | |
(getByte( 8) << 8) | |
(getByte(10) << 0); |
addr |= 0xC0000000; |
cpuSetPC(addr); |
run = false; |
break; |
case '8': |
/* S8 record: 3 byte start address (set PC, stop loading) */ |
addr = (getByte( 4) << 16) | |
(getByte( 6) << 8) | |
(getByte( 8) << 0); |
addr |= 0xC0000000; |
cpuSetPC(addr); |
run = false; |
break; |
case '9': |
/* S9 record: 2 byte start address (set PC, stop loading) */ |
addr = (getByte( 4) << 8) | |
(getByte( 6) << 0); |
addr |= 0xC0000000; |
cpuSetPC(addr); |
run = false; |
break; |
default: |
/* unknown type of S-record */ |
printf("Error: unknown type of S-record!\n"); |
run = false; |
break; |
} |
} |
serialOut(serno, 'q'); |
printf("Connection to load server closed.\n"); |
} |
/monitor/monitor-digilent/keyboard.s
0,0 → 1,149
; |
; keyboard.s -- a PC keyboard as input device |
; |
|
;*************************************************************** |
|
.set kbdbase,0xF0200000 ; keyboard base address |
|
; .import cout |
; .import byteout |
|
.import xltbl1 ; kbd translation table 1 |
.import xltbl2 ; kbd translation table 2 |
|
.export kbdinit ; initialize keyboard |
.export kbdinchk ; check if input available |
.export kbdin ; do keyboard input |
|
;*************************************************************** |
|
.code |
.align 4 |
|
kbdinit: |
jr $31 |
|
kbdinchk: |
add $8,$0,kbdbase |
ldw $2,$8,0 |
and $2,$2,1 |
jr $31 |
|
kbdin: |
sub $29,$29,12 |
stw $31,$29,8 |
stw $16,$29,4 |
stw $17,$29,0 |
kbdin0: |
jal kbdinp |
add $16,$2,$0 ; key 1 in $16 |
add $8,$0,0xF0 |
bne $16,$8,kbdin2 |
kbdin1: |
jal kbdinp |
j kbdin0 |
kbdin2: |
jal kbdinp |
add $17,$2,$0 ; key 2 in $17 |
beq $17,$16,kbdin2 |
add $8,$0,0xF0 |
beq $17,$8,kbdin3 |
j kbdin5 |
kbdin3: |
jal kbdinp |
bne $2,$16,kbdin2 |
kbdin4: |
add $4,$16,$0 ; use key 1 |
add $5,$0,xltbl1 ; with translation table 1 |
jal xlat |
j kbdx |
kbdin5: |
jal kbdinp |
add $8,$0,0xF0 |
bne $2,$8,kbdin5 |
kbdin6: |
jal kbdinp |
beq $2,$16,kbdin7 |
beq $2,$17,kbdin9 |
j kbdin5 |
kbdin7: |
jal kbdinp |
add $8,$0,0xF0 |
bne $2,$8,kbdin7 |
kbdin8: |
jal kbdinp |
bne $2,$17,kbdin7 |
j kbdin11 |
kbdin9: |
jal kbdinp |
add $8,$0,0xF0 |
bne $2,$8,kbdin9 |
kbdin10: |
jal kbdinp |
bne $2,$16,kbdin9 |
j kbdin11 |
kbdin11: |
add $8,$0,0x12 ; left shift key |
beq $16,$8,kbdin12 |
add $8,$0,0x59 ; right shift key |
beq $16,$8,kbdin12 |
add $8,$0,0x14 ; ctrl key |
beq $16,$8,kbdin14 |
j kbdin13 |
kbdin12: |
add $4,$17,$0 ; use key 2 |
add $5,$0,xltbl2 ; with translation table 2 |
jal xlat |
j kbdx |
kbdin13: |
add $4,$16,$0 ; use key 1 |
add $5,$0,xltbl1 ; with translation table 1 |
jal xlat |
j kbdx |
kbdin14: |
add $4,$17,$0 ; use key 2 |
add $5,$0,xltbl1 ; with translation table 1 |
jal xlat |
and $2,$2,0xFF-0x60 ; then reset bits 0x60 |
j kbdx |
kbdx: |
ldw $17,$29,0 |
ldw $16,$29,4 |
ldw $31,$29,8 |
add $29,$29,12 |
jr $31 |
|
kbdinp: |
add $8,$0,kbdbase |
kbdinp1: |
ldw $9,$8,0 |
and $9,$9,1 |
beq $9,$0,kbdinp1 ; wait until character ready |
ldw $2,$8,4 ; get character |
add $9,$0,0xE0 |
beq $2,$9,kbdinp1 ; ignore E0 prefix |
add $9,$0,0xE1 |
beq $2,$9,kbdinp1 ; as well as E1 prefix |
jr $31 |
|
xlat: |
sub $29,$29,8 |
stw $31,$29,4 |
stw $16,$29,0 |
and $16,$4,0xFF |
add $8,$16,$5 |
ldbu $2,$8,0 |
bne $2,$0,xlat1 |
; add $4,$0,'<' |
; jal cout |
; add $4,$16,$0 |
; jal byteout |
; add $4,$0,'>' |
; jal cout |
add $2,$16,$0 |
xlat1: |
ldw $16,$29,0 |
ldw $31,$29,4 |
add $29,$29,8 |
jr $31 |
/monitor/monitor-digilent/disasm.c
0,0 → 1,138
/* |
* disasm.c -- disassembler |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "instr.h" |
#include "disasm.h" |
|
|
static char instrBuffer[100]; |
|
|
static void disasmN(char *opName, Word immed) { |
if (immed == 0) { |
sprintf(instrBuffer, "%-7s", opName); |
} else { |
sprintf(instrBuffer, "%-7s %08X", opName, immed); |
} |
} |
|
|
static void disasmRH(char *opName, int r1, Half immed) { |
sprintf(instrBuffer, "%-7s $%d,%04X", opName, r1, immed); |
} |
|
|
static void disasmRHH(char *opName, int r1, Half immed) { |
sprintf(instrBuffer, "%-7s $%d,%08X", opName, r1, (Word) immed << 16); |
} |
|
|
static void disasmRRH(char *opName, int r1, int r2, Half immed) { |
sprintf(instrBuffer, "%-7s $%d,$%d,%04X", opName, r1, r2, immed); |
} |
|
|
static void disasmRRS(char *opName, int r1, int r2, Half immed) { |
sprintf(instrBuffer, "%-7s $%d,$%d,%s%04X", opName, r1, r2, |
SIGN(16) & immed ? "-" : "+", |
SIGN(16) & immed ? -(signed)SEXT16(immed) : SEXT16(immed)); |
} |
|
|
static void disasmRRR(char *opName, int r1, int r2, int r3) { |
sprintf(instrBuffer, "%-7s $%d,$%d,$%d", opName, r1, r2, r3); |
} |
|
|
static void disasmRRB(char *opName, int r1, int r2, Half offset, Word locus) { |
sprintf(instrBuffer, "%-7s $%d,$%d,%08X", opName, |
r1, r2, (locus + 4) + (SEXT16(offset) << 2)); |
} |
|
|
static void disasmJ(char *opName, Word offset, Word locus) { |
sprintf(instrBuffer, "%-7s %08X", opName, |
(locus + 4) + (SEXT26(offset) << 2)); |
} |
|
|
static void disasmJR(char *opName, int r1) { |
sprintf(instrBuffer, "%-7s $%d", opName, r1); |
} |
|
|
char *disasm(Word instr, Word locus) { |
Byte opcode; |
Instr *ip; |
|
opcode = (instr >> 26) & 0x3F; |
ip = instrCodeTbl[opcode]; |
if (ip == NULL) { |
disasmN("???", 0); |
} else { |
switch (ip->format) { |
case FORMAT_N: |
disasmN(ip->name, instr & 0x03FFFFFF); |
break; |
case FORMAT_RH: |
disasmRH(ip->name, (instr >> 16) & 0x1F, instr & 0x0000FFFF); |
break; |
case FORMAT_RHH: |
disasmRHH(ip->name, (instr >> 16) & 0x1F, instr & 0x0000FFFF); |
break; |
case FORMAT_RRH: |
disasmRRH(ip->name, (instr >> 16) & 0x1F, |
(instr >> 21) & 0x1F, instr & 0x0000FFFF); |
break; |
case FORMAT_RRS: |
disasmRRS(ip->name, (instr >> 16) & 0x1F, |
(instr >> 21) & 0x1F, instr & 0x0000FFFF); |
break; |
case FORMAT_RRR: |
disasmRRR(ip->name, (instr >> 11) & 0x1F, |
(instr >> 21) & 0x1F, (instr >> 16) & 0x1F); |
break; |
case FORMAT_RRX: |
if ((opcode & 1) == 0) { |
/* the FORMAT_RRR variant */ |
disasmRRR(ip->name, (instr >> 11) & 0x1F, |
(instr >> 21) & 0x1F, (instr >> 16) & 0x1F); |
} else { |
/* the FORMAT_RRH variant */ |
disasmRRH(ip->name, (instr >> 16) & 0x1F, |
(instr >> 21) & 0x1F, instr & 0x0000FFFF); |
} |
break; |
case FORMAT_RRY: |
if ((opcode & 1) == 0) { |
/* the FORMAT_RRR variant */ |
disasmRRR(ip->name, (instr >> 11) & 0x1F, |
(instr >> 21) & 0x1F, (instr >> 16) & 0x1F); |
} else { |
/* the FORMAT_RRS variant */ |
disasmRRS(ip->name, (instr >> 16) & 0x1F, |
(instr >> 21) & 0x1F, instr & 0x0000FFFF); |
} |
break; |
case FORMAT_RRB: |
disasmRRB(ip->name, (instr >> 21) & 0x1F, |
(instr >> 16) & 0x1F, instr & 0x0000FFFF, locus); |
break; |
case FORMAT_J: |
disasmJ(ip->name, instr & 0x03FFFFFF, locus); |
break; |
case FORMAT_JR: |
disasmJR(ip->name, (instr >> 21) & 0x1F); |
break; |
default: |
printf("illegal entry in instruction table\n"); |
break; |
} |
} |
return instrBuffer; |
} |
/monitor/monitor-digilent/sctio-ctl.s
0,0 → 1,133
; |
; sctio-ctl.s -- disk sector I/O for disk made available by disk controller |
; |
|
;*************************************************************** |
|
.set dskbase,0xF0400000 ; disk base address |
.set dskctrl,0 ; control register |
.set dskcnt,4 ; count register |
.set dsksct,8 ; sector register |
.set dskcap,12 ; capacity register |
.set dskbuf,0x00080000 ; disk buffer |
|
.set ctrlstrt,0x01 ; start bit |
.set ctrlien,0x02 ; interrupt enable bit |
.set ctrlwrt,0x04 ; write bit |
.set ctrlerr,0x08 ; error bit |
.set ctrldone,0x10 ; done bit |
.set ctrlrdy,0x20 ; ready bit |
|
.set sctsize,512 ; sector size in bytes |
|
.set retries,1000000 ; retries to get disk ready |
|
.export sctcapctl ; determine disk capacity |
.export sctioctl ; do disk I/O |
|
;*************************************************************** |
|
.code |
.align 4 |
|
sctcapctl: |
add $8,$0,retries ; set retry count |
add $9,$0,dskbase |
sctcap1: |
ldw $10,$9,dskctrl |
and $10,$10,ctrlrdy ; ready? |
bne $10,$0,sctcapok ; yes - jump |
sub $8,$8,1 |
bne $8,$0,sctcap1 ; try again |
add $2,$0,0 ; no disk found |
j sctcapx |
sctcapok: |
ldw $2,$9,dskcap ; get disk capacity |
sctcapx: |
jr $31 |
|
sctioctl: |
sub $29,$29,24 |
stw $31,$29,20 |
stw $16,$29,16 |
stw $17,$29,12 |
stw $18,$29,8 |
stw $19,$29,4 |
stw $20,$29,0 |
add $16,$4,$0 ; command |
add $17,$5,$0 ; sector number |
add $18,$6,0xC0000000 ; memory address, virtualized |
add $19,$7,$0 ; number of sectors |
|
add $8,$0,'r' |
beq $16,$8,sctrd |
add $8,$0,'w' |
beq $16,$8,sctwr |
add $2,$0,0xFF ; illegal command |
j sctx |
|
sctrd: |
add $2,$0,$0 ; return ok |
beq $19,$0,sctx ; if no (more) sectors |
add $8,$0,dskbase |
add $9,$0,1 |
stw $9,$8,dskcnt ; number of sectors |
stw $17,$8,dsksct ; sector number on disk |
add $9,$0,ctrlstrt |
stw $9,$8,dskctrl ; start command |
sctrd1: |
ldw $2,$8,dskctrl |
and $9,$2,ctrldone ; done? |
beq $9,$0,sctrd1 ; no - wait |
and $9,$2,ctrlerr ; error? |
bne $9,$0,sctx ; yes - leave |
add $8,$0,dskbase + dskbuf ; transfer data |
add $9,$0,sctsize |
sctrd2: |
ldw $10,$8,0 ; from disk buffer |
stw $10,$18,0 ; to memory |
add $8,$8,4 |
add $18,$18,4 |
sub $9,$9,4 |
bne $9,$0,sctrd2 |
add $17,$17,1 ; increment sector number |
sub $19,$19,1 ; decrement number of sectors |
j sctrd ; next sector |
|
sctwr: |
add $2,$0,$0 ; return ok |
beq $19,$0,sctx ; if no (more) sectors |
add $8,$0,dskbase + dskbuf ; transfer data |
add $9,$0,sctsize |
sctwr1: |
ldw $10,$18,0 ; from memory |
stw $10,$8,0 ; to disk buffer |
add $18,$18,4 |
add $8,$8,4 |
sub $9,$9,4 |
bne $9,$0,sctwr1 |
add $8,$0,dskbase |
add $9,$0,1 |
stw $9,$8,dskcnt ; number of sectors |
stw $17,$8,dsksct ; sector number on disk |
add $9,$0,ctrlwrt | ctrlstrt |
stw $9,$8,dskctrl ; start command |
sctwr2: |
ldw $2,$8,dskctrl |
and $9,$2,ctrldone ; done? |
beq $9,$0,sctwr2 ; no - wait |
and $9,$2,ctrlerr ; error? |
bne $9,$0,sctx ; yes - leave |
add $17,$17,1 ; increment sector number |
sub $19,$19,1 ; decrement number of sectors |
j sctwr ; next sector |
|
sctx: |
ldw $20,$29,0 |
ldw $19,$29,4 |
ldw $18,$29,8 |
ldw $17,$29,12 |
ldw $16,$29,16 |
ldw $31,$29,20 |
add $29,$29,24 |
jr $31 |
/monitor/monitor-digilent/load.h
0,0 → 1,13
/* |
* load.h -- load S-record file from serial line |
*/ |
|
|
#ifndef _LOAD_H_ |
#define _LOAD_H_ |
|
|
void load(int serno); |
|
|
#endif /* _LOAD_H_ */ |
/monitor/monitor-digilent/romlib.c
0,0 → 1,636
/* |
* romlib.c -- the ROM library |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "start.h" |
|
|
/**************************************************************/ |
|
|
/* |
* This is only for debugging. |
* Place a breakpoint at the very beginning of this routine |
* and call it wherever you want to break execution. |
*/ |
void debugBreak(void) { |
} |
|
|
/**************************************************************/ |
|
|
/* |
* Count the length of a string (without terminating null character). |
*/ |
int strlen(const char *s) { |
const char *p; |
|
p = s; |
while (*p != '\0') { |
p++; |
} |
return p - s; |
} |
|
|
/* |
* Compare two strings. |
* Return a number < 0, = 0, or > 0 iff the first string is less |
* than, equal to, or greater than the second one, respectively. |
*/ |
int strcmp(const char *s, const char *t) { |
while (*s == *t) { |
if (*s == '\0') { |
return 0; |
} |
s++; |
t++; |
} |
return *s - *t; |
} |
|
|
/* |
* Copy string t to string s (includes terminating null character). |
*/ |
char *strcpy(char *s, const char *t) { |
char *p; |
|
p = s; |
while ((*p = *t) != '\0') { |
p++; |
t++; |
} |
return s; |
} |
|
|
/* |
* Append string t to string s. |
*/ |
char *strcat(char *s, const char *t) { |
char *p; |
|
p = s; |
while (*p != '\0') { |
p++; |
} |
while ((*p = *t) != '\0') { |
p++; |
t++; |
} |
return s; |
} |
|
|
/* |
* Locate character c in string s. |
*/ |
char *strchr(const char *s, char c) { |
while (*s != c) { |
if (*s == '\0') { |
return NULL; |
} |
s++; |
} |
return (char *) s; |
} |
|
|
/* |
* Extract the next token from the string s, delimited |
* by any character from the delimiter string t. |
*/ |
char *strtok(char *s, const char *t) { |
static char *p; |
char *q; |
|
if (s != NULL) { |
p = s; |
} else { |
p++; |
} |
while (*p != '\0' && strchr(t, *p) != NULL) { |
p++; |
} |
if (*p == '\0') { |
return NULL; |
} |
q = p++; |
while (*p != '\0' && strchr(t, *p) == NULL) { |
p++; |
} |
if (*p != '\0') { |
*p = '\0'; |
} else { |
p--; |
} |
return q; |
} |
|
|
/**************************************************************/ |
|
|
/* |
* Determine if a character is 'white space'. |
*/ |
static Bool isspace(char c) { |
Bool res; |
|
switch (c) { |
case ' ': |
case '\f': |
case '\n': |
case '\r': |
case '\t': |
case '\v': |
res = true; |
break; |
default: |
res = false; |
break; |
} |
return res; |
} |
|
|
/* |
* Check for valid digit, and convert to value. |
*/ |
static Bool checkDigit(char c, int base, int *value) { |
if (c >= '0' && c <= '9') { |
*value = c - '0'; |
} else |
if (c >= 'A' && c <= 'Z') { |
*value = c - 'A' + 10; |
} else |
if (c >= 'a' && c <= 'z') { |
*value = c - 'a' + 10; |
} else { |
return false; |
} |
return *value < base; |
} |
|
|
/* |
* Convert initial part of string to unsigned long integer. |
*/ |
unsigned long strtoul(const char *s, char **endp, int base) { |
unsigned long res; |
int sign; |
int digit; |
|
res = 0; |
while (isspace(*s)) { |
s++; |
} |
if (*s == '+') { |
sign = 1; |
s++; |
} else |
if (*s == '-') { |
sign = -1; |
s++; |
} else { |
sign = 1; |
} |
if (base == 0 || base == 16) { |
if (*s == '0' && |
(*(s + 1) == 'x' || *(s + 1) == 'X')) { |
/* base is 16 */ |
s += 2; |
base = 16; |
} else { |
/* base is 0 or 16, but number does not start with "0x" */ |
if (base == 0) { |
if (*s == '0') { |
s++; |
base = 8; |
} else { |
base = 10; |
} |
} else { |
/* take base as is */ |
} |
} |
} else { |
/* take base as is */ |
} |
while (checkDigit(*s, base, &digit)) { |
res *= base; |
res += digit; |
s++; |
} |
if (endp != NULL) { |
*endp = (char *) s; |
} |
return sign * res; |
} |
|
|
/**************************************************************/ |
|
|
/* |
* Exchange two array items of a given size. |
*/ |
static void xchg(char *p, char *q, int size) { |
char t; |
|
while (size--) { |
t = *p; |
*p++ = *q; |
*q++ = t; |
} |
} |
|
|
/* |
* This is a recursive version of quicksort. |
*/ |
static void sort(char *l, char *r, int size, |
int (*cmp)(const void *, const void *)) { |
char *i; |
char *j; |
char *x; |
|
i = l; |
j = r; |
x = l + (((r - l) / size) / 2) * size; |
do { |
while (cmp(i, x) < 0) { |
i += size; |
} |
while (cmp(x, j) < 0) { |
j -= size; |
} |
if (i <= j) { |
/* exchange array elements i and j */ |
/* attention: update x if it is one of these */ |
if (x == i) { |
x = j; |
} else |
if (x == j) { |
x = i; |
} |
xchg(i, j, size); |
i += size; |
j -= size; |
} |
} while (i <= j); |
if (l < j) { |
sort(l, j, size, cmp); |
} |
if (i < r) { |
sort(i, r, size, cmp); |
} |
} |
|
|
/* |
* External interface for the quicksort algorithm. |
*/ |
void qsort(void *base, int n, int size, |
int (*cmp)(const void *, const void*)) { |
sort((char *) base, (char *) base + (n - 1) * size, size, cmp); |
} |
|
|
/**************************************************************/ |
|
|
/* |
* Input a character from the console. |
*/ |
char getchar(void) { |
return cin(); |
} |
|
|
/* |
* Output a character on the console. |
* Replace LF by CR/LF. |
*/ |
void putchar(char c) { |
if (c == '\n') { |
cout('\r'); |
} |
cout(c); |
} |
|
|
/* |
* Output a string on the console. |
* Replace LF by CR/LF. |
*/ |
void puts(const char *s) { |
while (*s != '\0') { |
putchar(*s); |
s++; |
} |
} |
|
|
/**************************************************************/ |
|
|
/* |
* Count the number of characters needed to represent |
* a given number in base 10. |
*/ |
static int countPrintn(long n) { |
long a; |
int res; |
|
res = 0; |
if (n < 0) { |
res++; |
n = -n; |
} |
a = n / 10; |
if (a != 0) { |
res += countPrintn(a); |
} |
return res + 1; |
} |
|
|
/* |
* Output a number in base 10. |
*/ |
static void *printn(void *(*emit)(void *, char), void *arg, |
int *nchar, long n) { |
long a; |
|
if (n < 0) { |
arg = emit(arg, '-'); |
(*nchar)++; |
n = -n; |
} |
a = n / 10; |
if (a != 0) { |
arg = printn(emit, arg, nchar, a); |
} |
arg = emit(arg, n % 10 + '0'); |
(*nchar)++; |
return arg; |
} |
|
|
/* |
* Count the number of characters needed to represent |
* a given number in a given base. |
*/ |
static int countPrintu(unsigned long n, unsigned long b) { |
unsigned long a; |
int res; |
|
res = 0; |
a = n / b; |
if (a != 0) { |
res += countPrintu(a, b); |
} |
return res + 1; |
} |
|
|
/* |
* Output a number in a given base. |
*/ |
static void *printu(void *(*emit)(void *, char), void *arg, |
int *nchar, unsigned long n, unsigned long b, |
Bool upperCase) { |
unsigned long a; |
|
a = n / b; |
if (a != 0) { |
arg = printu(emit, arg, nchar, a, b, upperCase); |
} |
if (upperCase) { |
arg = emit(arg, "0123456789ABCDEF"[n % b]); |
(*nchar)++; |
} else { |
arg = emit(arg, "0123456789abcdef"[n % b]); |
(*nchar)++; |
} |
return arg; |
} |
|
|
/* |
* Output a number of filler characters. |
*/ |
static void *fill(void *(*emit)(void *, char), void *arg, |
int *nchar, int numFillers, char filler) { |
while (numFillers-- > 0) { |
arg = emit(arg, filler); |
(*nchar)++; |
} |
return arg; |
} |
|
|
/* |
* This function does the real work of formatted printing. |
*/ |
static int doPrintf(void *(*emit)(void *, char), void *arg, |
const char *fmt, va_list ap) { |
int nchar; |
char c; |
int n; |
long ln; |
unsigned int u; |
unsigned long lu; |
char *s; |
Bool negFlag; |
char filler; |
int width, count; |
|
nchar = 0; |
while (1) { |
while ((c = *fmt++) != '%') { |
if (c == '\0') { |
return nchar; |
} |
arg = emit(arg, c); |
nchar++; |
} |
c = *fmt++; |
if (c == '-') { |
negFlag = true; |
c = *fmt++; |
} else { |
negFlag = false; |
} |
if (c == '0') { |
filler = '0'; |
c = *fmt++; |
} else { |
filler = ' '; |
} |
width = 0; |
while (c >= '0' && c <= '9') { |
width *= 10; |
width += c - '0'; |
c = *fmt++; |
} |
if (c == 'd') { |
n = va_arg(ap, int); |
count = countPrintn(n); |
if (width > 0 && !negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
arg = printn(emit, arg, &nchar, n); |
if (width > 0 && negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
} else |
if (c == 'u' || c == 'o' || c == 'x' || c == 'X') { |
u = va_arg(ap, int); |
count = countPrintu(u, |
c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10)); |
if (width > 0 && !negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
arg = printu(emit, arg, &nchar, u, |
c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10), |
c == 'X'); |
if (width > 0 && negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
} else |
if (c == 'l') { |
c = *fmt++; |
if (c == 'd') { |
ln = va_arg(ap, long); |
count = countPrintn(ln); |
if (width > 0 && !negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
arg = printn(emit, arg, &nchar, ln); |
if (width > 0 && negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
} else |
if (c == 'u' || c == 'o' || c == 'x' || c == 'X') { |
lu = va_arg(ap, long); |
count = countPrintu(lu, |
c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10)); |
if (width > 0 && !negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
arg = printu(emit, arg, &nchar, lu, |
c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10), |
c == 'X'); |
if (width > 0 && negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
} else { |
arg = emit(arg, 'l'); |
nchar++; |
arg = emit(arg, c); |
nchar++; |
} |
} else |
if (c == 's') { |
s = va_arg(ap, char *); |
count = strlen(s); |
if (width > 0 && !negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
while ((c = *s++) != '\0') { |
arg = emit(arg, c); |
nchar++; |
} |
if (width > 0 && negFlag) { |
arg = fill(emit, arg, &nchar, width - count, filler); |
} |
} else |
if (c == 'c') { |
c = va_arg(ap, char); |
arg = emit(arg, c); |
nchar++; |
} else { |
arg = emit(arg, c); |
nchar++; |
} |
} |
/* never reached */ |
return 0; |
} |
|
|
/* |
* Emit a character to the console. |
*/ |
static void *emitToConsole(void *dummy, char c) { |
putchar(c); |
return dummy; |
} |
|
|
/* |
* Formatted output with a variable argument list. |
*/ |
int vprintf(const char *fmt, va_list ap) { |
int n; |
|
n = doPrintf(emitToConsole, NULL, fmt, ap); |
return n; |
} |
|
|
/* |
* Formatted output. |
*/ |
int printf(const char *fmt, ...) { |
int n; |
va_list ap; |
|
va_start(ap, fmt); |
n = vprintf(fmt, ap); |
va_end(ap); |
return n; |
} |
|
|
/* |
* Emit a character to a buffer. |
*/ |
static void *emitToBuffer(void *bufptr, char c) { |
*(char *)bufptr = c; |
return (char *) bufptr + 1; |
} |
|
|
/* |
* Formatted output into a buffer with a variable argument list. |
*/ |
int vsprintf(char *s, const char *fmt, va_list ap) { |
int n; |
|
n = doPrintf(emitToBuffer, s, fmt, ap); |
s[n] = '\0'; |
return n; |
} |
|
|
/* |
* Formatted output into a buffer. |
*/ |
int sprintf(char *s, const char *fmt, ...) { |
int n; |
va_list ap; |
|
va_start(ap, fmt); |
n = vsprintf(s, fmt, ap); |
va_end(ap); |
return n; |
} |
/monitor/monitor-digilent/serial.h
0,0 → 1,21
/* |
* serial.s -- the serial line interface |
*/ |
|
|
#ifndef _SERIAL_H_ |
#define _SERIAL_H_ |
|
|
int ser0inchk(void); |
int ser0in(void); |
int ser0outchk(void); |
void ser0out(int c); |
|
int ser1inchk(void); |
int ser1in(void); |
int ser1outchk(void); |
void ser1out(int c); |
|
|
#endif /* _SERIAL_H_ */ |
/monitor/monitor-digilent/display.s
0,0 → 1,225
; |
; display.s -- a memory-mapped alphanumerical display |
; |
|
;*************************************************************** |
|
.set dspbase,0xF0100000 ; display base address |
|
.export dspinit ; initialize display |
.export dspoutchk ; check for output possible |
.export dspout ; do display output |
|
;*************************************************************** |
|
.code |
.align 4 |
|
; initialize display |
dspinit: |
sub $29,$29,4 |
stw $31,$29,0 |
jal clrscr |
add $8,$0,scrrow |
stw $0,$8,0 |
add $8,$0,scrcol |
stw $0,$8,0 |
jal calcp |
jal stcrs |
ldw $31,$29,0 |
add $29,$29,4 |
jr $31 |
|
; check if a character can be written |
dspoutchk: |
add $2,$0,1 |
jr $31 |
|
; output a character on the display |
dspout: |
sub $29,$29,8 |
stw $31,$29,4 |
stw $16,$29,0 |
and $16,$4,0xFF |
jal rmcrs |
add $8,$0,' ' |
bltu $16,$8,dspout2 |
add $8,$0,scrptr |
ldw $9,$8,0 |
or $16,$16,0x07 << 8 |
stw $16,$9,0 |
add $9,$9,4 |
stw $9,$8,0 |
add $8,$0,scrcol |
ldw $9,$8,0 |
add $9,$9,1 |
stw $9,$8,0 |
add $10,$0,80 |
bne $9,$10,dspout1 |
jal docr |
jal dolf |
dspout1: |
jal stcrs |
ldw $16,$29,0 |
ldw $31,$29,4 |
add $29,$29,8 |
jr $31 |
|
dspout2: |
add $8,$0,0x0D |
bne $16,$8,dspout3 |
jal docr |
j dspout1 |
|
dspout3: |
add $8,$0,0x0A |
bne $16,$8,dspout4 |
jal dolf |
j dspout1 |
|
dspout4: |
add $8,$0,0x08 |
bne $16,$8,dspout5 |
jal dobs |
j dspout1 |
|
dspout5: |
j dspout1 |
|
; do carriage return |
docr: |
sub $29,$29,4 |
stw $31,$29,0 |
add $8,$0,scrcol |
stw $0,$8,0 |
jal calcp |
ldw $31,$29,0 |
add $29,$29,4 |
jr $31 |
|
; do linefeed |
dolf: |
sub $29,$29,4 |
stw $31,$29,0 |
add $8,$0,scrrow |
ldw $9,$8,0 |
add $10,$0,29 |
beq $9,$10,dolf1 |
add $9,$9,1 |
stw $9,$8,0 |
jal calcp |
j dolf2 |
dolf1: |
jal scrscr |
dolf2: |
ldw $31,$29,0 |
add $29,$29,4 |
jr $31 |
|
; do backspace |
dobs: |
sub $29,$29,4 |
stw $31,$29,0 |
add $8,$0,scrcol |
ldw $9,$8,0 |
beq $9,$0,dobs1 |
sub $9,$9,1 |
stw $9,$8,0 |
jal calcp |
dobs1: |
ldw $31,$29,0 |
add $29,$29,4 |
jr $31 |
|
; remove cursor |
rmcrs: |
add $8,$0,scrptr |
ldw $8,$8,0 |
add $9,$0,scrchr |
ldw $10,$9,0 |
stw $10,$8,0 |
jr $31 |
|
; set cursor |
stcrs: |
add $8,$0,scrptr |
ldw $8,$8,0 |
add $9,$0,scrchr |
ldw $10,$8,0 |
stw $10,$9,0 |
add $10,$0,(0x87 << 8) | '_' |
stw $10,$8,0 |
jr $31 |
|
; calculate screen pointer based on row and column |
calcp: |
add $9,$0,dspbase |
add $8,$0,scrrow |
ldw $10,$8,0 |
sll $10,$10,7+2 |
add $9,$9,$10 |
add $8,$0,scrcol |
ldw $10,$8,0 |
sll $10,$10,0+2 |
add $9,$9,$10 |
add $8,$0,scrptr |
stw $9,$8,0 |
jr $31 |
|
; clear screen |
clrscr: |
add $11,$0,(0x07 << 8) | ' ' |
add $8,$0,dspbase |
add $9,$0,30 |
clrscr1: |
add $10,$0,80 |
clrscr2: |
stw $11,$8,0 |
add $8,$8,4 |
sub $10,$10,1 |
bne $10,$0,clrscr2 |
add $8,$8,(128-80)*4 |
sub $9,$9,1 |
bne $9,$0,clrscr1 |
jr $31 |
|
; scroll screen |
scrscr: |
add $8,$0,dspbase |
add $9,$0,29 |
scrscr1: |
add $10,$0,80 |
scrscr2: |
ldw $11,$8,128*4 |
stw $11,$8,0 |
add $8,$8,4 |
sub $10,$10,1 |
bne $10,$0,scrscr2 |
add $8,$8,(128-80)*4 |
sub $9,$9,1 |
bne $9,$0,scrscr1 |
add $11,$0,(0x07 << 8) | ' ' |
add $10,$0,80 |
scrscr3: |
stw $11,$8,0 |
add $8,$8,4 |
sub $10,$10,1 |
bne $10,$0,scrscr3 |
jr $31 |
|
;*************************************************************** |
|
.bss |
.align 4 |
|
scrptr: |
.word 0 |
|
scrrow: |
.word 0 |
|
scrcol: |
.word 0 |
|
scrchr: |
.word 0 |
/monitor/monitor-digilent/disasm.h
0,0 → 1,13
/* |
* disasm.h -- disassembler |
*/ |
|
|
#ifndef _DISASM_H_ |
#define _DISASM_H_ |
|
|
char *disasm(Word instr, Word locus); |
|
|
#endif /* _DISASM_H_ */ |
/monitor/monitor-digilent/end.s
0,0 → 1,19
; |
; end.s -- end-of-segment labels |
; |
|
.export _ecode |
.export _edata |
.export _ebss |
|
.code |
.align 4 |
_ecode: |
|
.data |
.align 4 |
_edata: |
|
.bss |
.align 4 |
_ebss: |
/monitor/monitor-digilent/cpu.c
0,0 → 1,367
/* |
* cpu.c -- execute instructions |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "instr.h" |
#include "cpu.h" |
#include "mmu.h" |
#include "start.h" |
|
|
#define RR(n) r[n] |
#define WR(n,d) ((void) ((n) != 0 ? r[n] = (d) : (d))) |
|
#define BREAK (OP_TRAP << 26) |
|
|
/**************************************************************/ |
|
|
static Word pc; /* program counter */ |
static Word psw; /* processor status word */ |
static Word r[32]; /* general purpose registers */ |
|
static Bool breakSet; /* breakpoint set if true */ |
static Word breakAddr; /* if breakSet, this is where */ |
|
|
/**************************************************************/ |
|
|
Word cpuGetPC(void) { |
return pc; |
} |
|
|
void cpuSetPC(Word addr) { |
pc = addr; |
} |
|
|
Word cpuGetReg(int regnum) { |
return RR(regnum & 0x1F); |
} |
|
|
void cpuSetReg(int regnum, Word value) { |
WR(regnum & 0x1F, value); |
} |
|
|
Word cpuGetPSW(void) { |
return psw; |
} |
|
|
void cpuSetPSW(Word value) { |
psw = value; |
} |
|
|
Bool cpuTestBreak(void) { |
return breakSet; |
} |
|
|
Word cpuGetBreak(void) { |
return breakAddr; |
} |
|
|
void cpuSetBreak(Word addr) { |
breakAddr = addr; |
breakSet = true; |
} |
|
|
void cpuResetBreak(void) { |
breakSet = false; |
} |
|
|
/**************************************************************/ |
|
|
static char *cause[32] = { |
/* 0 */ "terminal 0 transmitter interrupt", |
/* 1 */ "terminal 0 receiver interrupt", |
/* 2 */ "terminal 1 transmitter interrupt", |
/* 3 */ "terminal 1 receiver interrupt", |
/* 4 */ "keyboard interrupt", |
/* 5 */ "unknown interrupt", |
/* 6 */ "unknown interrupt", |
/* 7 */ "unknown interrupt", |
/* 8 */ "disk interrupt", |
/* 9 */ "unknown interrupt", |
/* 10 */ "unknown interrupt", |
/* 11 */ "unknown interrupt", |
/* 12 */ "unknown interrupt", |
/* 13 */ "unknown interrupt", |
/* 14 */ "timer interrupt", |
/* 15 */ "unknown interrupt", |
/* 16 */ "bus timeout exception", |
/* 17 */ "illegal instruction exception", |
/* 18 */ "privileged instruction exception", |
/* 19 */ "divide instruction exception", |
/* 20 */ "trap instruction exception", |
/* 21 */ "TLB miss exception", |
/* 22 */ "TLB write exception", |
/* 23 */ "TLB invalid exception", |
/* 24 */ "illegal address exception", |
/* 25 */ "privileged address exception", |
/* 26 */ "unknown exception", |
/* 27 */ "unknown exception", |
/* 28 */ "unknown exception", |
/* 29 */ "unknown exception", |
/* 30 */ "unknown exception", |
/* 31 */ "unknown exception" |
}; |
|
|
char *exceptionToString(int exception) { |
if (exception < 0 || |
exception >= sizeof(cause)/sizeof(cause[0])) { |
return "<exception number out of bounds>"; |
} |
return cause[exception]; |
} |
|
|
/**************************************************************/ |
|
|
static Byte stepType[64] = { |
/* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ |
/* 0x00 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, |
/* 0x10 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, |
/* 0x20 */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 4, 3, 4, 1, 0, |
/* 0x30 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, |
}; |
|
|
static Bool evalCond(int cc, Word a, Word b) { |
switch (cc) { |
case 0: |
/* equal */ |
if (a == b) { |
return true; |
} |
break; |
case 1: |
/* not equal */ |
if (a != b) { |
return true; |
} |
break; |
case 2: |
/* less or equal (signed) */ |
if ((signed int) a <= (signed int) b) { |
return true; |
} |
break; |
case 3: |
/* less or equal (unsigned) */ |
if (a <= b) { |
return true; |
} |
break; |
case 4: |
/* less than (signed) */ |
if ((signed int) a < (signed int) b) { |
return true; |
} |
break; |
case 5: |
/* less than (unsigned) */ |
if (a < b) { |
return true; |
} |
break; |
case 6: |
/* greater or equal (signed) */ |
if ((signed int) a >= (signed int) b) { |
return true; |
} |
break; |
case 7: |
/* greater or equal (unsigned) */ |
if (a >= b) { |
return true; |
} |
break; |
case 8: |
/* greater than (signed) */ |
if ((signed int) a > (signed int) b) { |
return true; |
} |
break; |
case 9: |
/* greater than (unsigned) */ |
if (a > b) { |
return true; |
} |
break; |
default: |
printf("cannot compute condition code %d\n", cc); |
break; |
} |
return false; |
} |
|
|
Bool cpuStep(void) { |
Word instr; |
int opcode; |
int reg1, reg2; |
Half immed; |
Word offset; |
Bool canStep; |
Word nextAddr; |
Word nextInstr; |
int i; |
MonitorState stepState; |
MonitorState *origReturn; |
|
instr = mmuReadWord(pc); |
opcode = (instr >> 26) & 0x3F; |
reg1 = (instr >> 21) & 0x1F; |
reg2 = (instr >> 16) & 0x1F; |
immed = instr & 0x0000FFFF; |
offset = instr & 0x03FFFFFF; |
canStep = true; |
switch (stepType[opcode]) { |
case 1: |
/* next instruction follows current one */ |
nextAddr = pc + 4; |
break; |
case 2: |
/* next instruction conditionally reached by PC relative branch */ |
nextAddr = pc + 4; |
if (evalCond(opcode - OP_BEQ, RR(reg1), RR(reg2))) { |
nextAddr += SEXT16(immed) << 2; |
} |
break; |
case 3: |
/* next instruction reached by PC relative jump */ |
nextAddr = pc + 4 + (SEXT26(offset) << 2); |
break; |
case 4: |
/* next instruction reached by jump to register contents */ |
nextAddr = RR(reg1); |
break; |
default: |
printf("cannot single-step instruction with opcode 0x%02X\n", |
opcode); |
canStep = false; |
break; |
} |
if (!canStep) { |
return false; |
} |
nextInstr = mmuReadWord(nextAddr); |
mmuWriteWord(nextAddr, BREAK); |
for (i = 0; i < 32; i++) { |
userContext.reg[i] = RR(i); |
} |
userContext.reg[30] = pc; |
userContext.psw = psw & ~PSW_V; |
userContext.tlbIndex = mmuGetIndex(); |
userContext.tlbHi = mmuGetEntryHi(); |
userContext.tlbLo = mmuGetEntryLo(); |
if (saveState(&stepState)) { |
origReturn = monitorReturn; |
monitorReturn = &stepState; |
resume(); |
} |
monitorReturn = origReturn; |
for (i = 0; i < 32; i++) { |
WR(i, userContext.reg[i]); |
} |
pc = userContext.reg[30]; |
psw = userContext.psw | (psw & PSW_V); |
mmuSetIndex(userContext.tlbIndex); |
mmuSetEntryHi(userContext.tlbHi); |
mmuSetEntryLo(userContext.tlbLo); |
mmuWriteWord(nextAddr, nextInstr); |
if (nextAddr == pc) { |
return true; |
} |
if ((psw & PSW_V) == 0) { |
printf("unexpected %s occurred\n", |
exceptionToString((psw & PSW_PRIO_MASK) >> 16)); |
return false; |
} |
if ((psw & PSW_PRIO_MASK) >> 16 == 21 && |
(mmuGetEntryHi() & 0x80000000) == 0) { |
pc = 0xC0000008; |
} else { |
pc = 0xC0000004; |
} |
return true; |
} |
|
|
Bool cpuRun(void) { |
Word instr; |
int i; |
MonitorState runState; |
MonitorState *origReturn; |
|
if (breakSet && breakAddr == pc) { |
/* single-step one instruction */ |
if (!cpuStep()) { |
return false; |
} |
} |
while (1) { |
if (breakSet) { |
instr = mmuReadWord(breakAddr); |
mmuWriteWord(breakAddr, BREAK); |
} |
for (i = 0; i < 32; i++) { |
userContext.reg[i] = RR(i); |
} |
userContext.reg[30] = pc; |
userContext.psw = psw & ~PSW_V; |
userContext.tlbIndex = mmuGetIndex(); |
userContext.tlbHi = mmuGetEntryHi(); |
userContext.tlbLo = mmuGetEntryLo(); |
if (saveState(&runState)) { |
origReturn = monitorReturn; |
monitorReturn = &runState; |
resume(); |
} |
monitorReturn = origReturn; |
for (i = 0; i < 32; i++) { |
WR(i, userContext.reg[i]); |
} |
pc = userContext.reg[30]; |
psw = userContext.psw | (psw & PSW_V); |
mmuSetIndex(userContext.tlbIndex); |
mmuSetEntryHi(userContext.tlbHi); |
mmuSetEntryLo(userContext.tlbLo); |
if (breakSet) { |
mmuWriteWord(breakAddr, instr); |
} |
if (breakSet && breakAddr == pc) { |
return true; |
} |
if ((psw & PSW_V) == 0) { |
printf("unexpected %s occurred\n", |
exceptionToString((psw & PSW_PRIO_MASK) >> 16)); |
return false; |
} |
if ((psw & PSW_PRIO_MASK) >> 16 == 21 && |
(mmuGetEntryHi() & 0x80000000) == 0) { |
pc = 0xC0000008; |
} else { |
pc = 0xC0000004; |
} |
} |
/* never reached */ |
return false; |
} |
/monitor/monitor-digilent/getline.c
0,0 → 1,136
/* |
* getline.c -- line input |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "getline.h" |
|
|
#define MAX_HISTORY 20 |
|
|
static char history[MAX_HISTORY][80]; |
static int historyIndex; /* next line to be written */ |
|
|
/* |
* Get a line from the console. |
*/ |
char *getLine(char *prompt) { |
static char line[80]; |
int index; |
int historyPointer; |
char c; |
int i; |
|
printf(prompt); |
index = 0; |
historyPointer = historyIndex; |
while (1) { |
c = getchar(); |
switch (c) { |
case '\r': |
putchar('\n'); |
line[index] = '\0'; |
return line; |
case '\b': |
case 0x7F: |
if (index == 0) { |
break; |
} |
putchar('\b'); |
putchar(' '); |
putchar('\b'); |
index--; |
break; |
case 'P' & ~0x40: |
if (historyPointer == historyIndex) { |
line[index] = '\0'; |
strcpy(history[historyIndex], line); |
} |
i = historyPointer - 1; |
if (i == -1) { |
i = MAX_HISTORY - 1; |
} |
if (i == historyIndex) { |
putchar('\a'); |
break; |
} |
if (history[i][0] == '\0') { |
putchar('\a'); |
break; |
} |
historyPointer = i; |
strcpy(line, history[historyPointer]); |
printf("\r"); |
for (i = 0; i < 79; i++) { |
printf(" "); |
} |
printf("\r"); |
printf(prompt); |
printf(line); |
index = strlen(line); |
break; |
case 'N' & ~0x40: |
if (historyPointer == historyIndex) { |
putchar('\a'); |
break; |
} |
i = historyPointer + 1; |
if (i == MAX_HISTORY) { |
i = 0; |
} |
historyPointer = i; |
strcpy(line, history[historyPointer]); |
printf("\r"); |
for (i = 0; i < 79; i++) { |
printf(" "); |
} |
printf("\r"); |
printf(prompt); |
printf(line); |
index = strlen(line); |
break; |
default: |
if (c == '\t') { |
c = ' '; |
} |
if (c < 0x20 || c > 0x7E) { |
break; |
} |
putchar(c); |
line[index++] = c; |
break; |
} |
} |
/* never reached */ |
return NULL; |
} |
|
|
/* |
* Add a line to the history. |
* Don't do this if the line is empty, or if its |
* contents exactly match the previous line. |
*/ |
void addHist(char *line) { |
int lastWritten; |
|
if (*line == '\0') { |
return; |
} |
lastWritten = historyIndex - 1; |
if (lastWritten == -1) { |
lastWritten = MAX_HISTORY - 1; |
} |
if (strcmp(history[lastWritten], line) == 0) { |
return; |
} |
strcpy(history[historyIndex], line); |
if (++historyIndex == MAX_HISTORY) { |
historyIndex = 0; |
} |
} |
/monitor/monitor-digilent/romlib.h
0,0 → 1,34
/* |
* romlib.h -- the ROM library |
*/ |
|
|
#ifndef _ROMLIB_H_ |
#define _ROMLIB_H_ |
|
|
void debugBreak(void); |
|
int strlen(const char *s); |
int strcmp(const char *s, const char *t); |
char *strcpy(char *s, const char *t); |
char *strcat(char *s, const char *t); |
char *strchr(const char *s, char c); |
char *strtok(char *s, const char *t); |
|
unsigned long strtoul(const char *s, char **endp, int base); |
|
void qsort(void *base, int n, int size, |
int (*cmp)(const void *, const void *)); |
|
char getchar(void); |
void putchar(char c); |
void puts(const char *s); |
|
int vprintf(const char *fmt, va_list ap); |
int printf(const char *fmt, ...); |
int vsprintf(char *s, const char *fmt, va_list ap); |
int sprintf(char *s, const char *fmt, ...); |
|
|
#endif /* _ROMLIB_H_ */ |
/monitor/monitor-digilent/cpu.h
0,0 → 1,40
/* |
* cpu.h -- execute instructions |
*/ |
|
|
#ifndef _CPU_H_ |
#define _CPU_H_ |
|
|
#define PSW_V 0x08000000 /* interrupt vector bit in PSW */ |
#define PSW_UM 0x04000000 /* user mode enable bit in PSW */ |
#define PSW_PUM 0x02000000 /* previous value of PSW_UM */ |
#define PSW_OUM 0x01000000 /* old value of PSW_UM */ |
#define PSW_IE 0x00800000 /* interrupt enable bit in PSW */ |
#define PSW_PIE 0x00400000 /* previous value of PSW_IE */ |
#define PSW_OIE 0x00200000 /* old value of PSW_IE */ |
#define PSW_PRIO_MASK 0x001F0000 /* bits to encode IRQ prio in PSW */ |
|
|
Word cpuGetPC(void); |
void cpuSetPC(Word addr); |
|
Word cpuGetReg(int regnum); |
void cpuSetReg(int regnum, Word value); |
|
Word cpuGetPSW(void); |
void cpuSetPSW(Word value); |
|
Bool cpuTestBreak(void); |
Word cpuGetBreak(void); |
void cpuSetBreak(Word addr); |
void cpuResetBreak(void); |
|
char *exceptionToString(int exception); |
|
Bool cpuStep(void); |
Bool cpuRun(void); |
|
|
#endif /* _CPU_H_ */ |
/monitor/monitor-digilent/getline.h
0,0 → 1,14
/* |
* getline.h -- line input |
*/ |
|
|
#ifndef _GETLINE_H_ |
#define _GETLINE_H_ |
|
|
char *getLine(char *prompt); |
void addHist(char *line); |
|
|
#endif /* _GETLINE_H_ */ |
/monitor/monitor-digilent/Makefile
0,0 → 1,31
# |
# Makefile for ECO32 ROM monitor |
# |
|
BUILD = ../../build |
|
SRC = start.s main.c command.c instr.c asm.c disasm.c \ |
load.c boot.c cpu.c mmu.c getline.c romlib.c \ |
keyboard.s ../kbdtbls/kbdtbls.s display.s \ |
serial.s sctio-ctl.s sctio-ser.s end.s |
|
.PHONY: all install clean |
|
all: monitor.bin monitor.exo |
|
install: monitor.bin monitor.exo |
mkdir -p $(BUILD)/monitor |
cp monitor.bin $(BUILD)/monitor |
cp monitor.exo $(BUILD)/monitor |
|
monitor.exo: monitor.bin |
$(BUILD)/bin/bin2exo 0 monitor.bin monitor.exo |
|
monitor.bin: $(SRC) |
$(BUILD)/bin/lcc -A -Wo-rom -Wl-rd -Wl0xC3FFC000 \ |
-Wl-m -Wlmonitor.map -o monitor.bin $(SRC) |
|
clean: |
rm -f *~ |
rm -f monitor.map monitor.bin |
rm -f monitor.exo |
/monitor/monitor-digilent/serial.s
0,0 → 1,98
; |
; serial.s -- the serial line interface |
; |
|
;*************************************************************** |
|
.set ser0base,0xF0300000 ; serial line 0 base address |
.set ser1base,0xF0301000 ; serial line 1 base address |
|
.export serinit ; initialize serial interface |
|
.export ser0inchk ; line 0 input check |
.export ser0in ; line 0 input |
.export ser0outchk ; line 0 output check |
.export ser0out ; line 0 output |
|
.export ser1inchk ; line 1 input check |
.export ser1in ; line 1 input |
.export ser1outchk ; line 1 output check |
.export ser1out ; line 1 output |
|
;*************************************************************** |
|
.code |
.align 4 |
|
serinit: |
jr $31 |
|
;*************************************************************** |
|
.code |
.align 4 |
|
ser0inchk: |
add $8,$0,ser0base |
ldw $2,$8,0 |
and $2,$2,1 |
jr $31 |
|
ser0in: |
add $8,$0,ser0base |
ser0in1: |
ldw $9,$8,0 |
and $9,$9,1 |
beq $9,$0,ser0in1 |
ldw $2,$8,4 |
jr $31 |
|
ser0outchk: |
add $8,$0,ser0base |
ldw $2,$8,8 |
and $2,$2,1 |
jr $31 |
|
ser0out: |
add $8,$0,ser0base |
ser0out1: |
ldw $9,$8,8 |
and $9,$9,1 |
beq $9,$0,ser0out1 |
stw $4,$8,12 |
jr $31 |
|
;*************************************************************** |
|
.code |
.align 4 |
|
ser1inchk: |
add $8,$0,ser1base |
ldw $2,$8,0 |
and $2,$2,1 |
jr $31 |
|
ser1in: |
add $8,$0,ser1base |
ser1in1: |
ldw $9,$8,0 |
and $9,$9,1 |
beq $9,$0,ser1in1 |
ldw $2,$8,4 |
jr $31 |
|
ser1outchk: |
add $8,$0,ser1base |
ldw $2,$8,8 |
and $2,$2,1 |
jr $31 |
|
ser1out: |
add $8,$0,ser1base |
ser1out1: |
ldw $9,$8,8 |
and $9,$9,1 |
beq $9,$0,ser1out1 |
stw $4,$8,12 |
jr $31 |
/monitor/monitor-digilent/monitor.exo
0,0 → 1,2259
S214000000A800000CA800009BA800009AA8001A07E9 |
S214000010A8001A0BA8001AFBA8001AFCA8001B9937 |
S214000020A8001B9DA8001BA3A8001BA7A800003BB8 |
S214000030A800003DE4000000E40000037C01C000CE |
S2140000400001400000004800040A0020E408000206 |
S214000050E4090001F400000005081000052900016D |
S214000060852AFFFA7C01C3FF4C21C0000001500026 |
S2140000707C01C3FF4C21DA7000014000090A4800E9 |
S2140000807C01E0004C2172B001214800A80000026B |
S214000090C12B0000D50B00000D0800040D2900043C |
S2140000A09D0AFFFB7C01C3FF4C21DA700001400073 |
S2140000B07C01C3FF4C21E5E000014800A8000002D7 |
S2140000C0D5000000050800049509FFFD7C01C4006A |
S2140000D00001E800B0001ABBB00019D3B0001B68DE |
S2140000E0B000008FABFFFFD3E4040001F000000077 |
S2140000F0E0020002AFE00000E4040001F0000000AF |
S214000100E0020003AFE00000E4040001E4050002A2 |
S214000110E4060003F4000000AFE000008480000165 |
S214000120A8001B8CA8001BE78480000500A0200008 |
S21400013000C0280000E03000C3A70010A8001B93F2 |
S21400014000A0200000C0280000E03000C3A7001078 |
S214000150A8001C11D49F0000D49D0004D490000871 |
S214000160D491000CD4920010D4930014D4940018A8 |
S214000170D495001CD4960020D497002404020001D5 |
S214000180AFE000007C01C3FF4C21DA7000200800BD |
S214000190C02800008100FFFBC11F0000C11D000435 |
S2140001A0C1100008C111000CC1120010C1130014C8 |
S2140001B0C1140018C115001CC1160020C117002468 |
S2140001C004020000AFE00000E40000007C01C3FF72 |
S2140001D04C21DA740001E000C3880084E4080001C2 |
S2140001E0C3880088E4080002C388008CE408000383 |
S2140001F0C3810004C3820008C383000CC3840010BC |
S214000200C3850014C3860018C387001CC38800205B |
S214000210C3890024C38A0028C38B002CC38C0030FB |
S214000220C38D0034C38E0038C38F003CC39000409B |
S214000230C3910044C3920048C393004CC39400503B |
S214000240C3950054C3960058C397005CC3980060DB |
S214000250C3990064C39A0068C39B006CC39D007476 |
S214000260C39E0078C39F007CC39C0080E41C0000F3 |
S214000270BC0000007C1CC3FF4F9CDA74D7800000D3 |
S214000280D7810004D7820008D783000CD7840010DB |
S214000290D7850014D7860018D787001CD78800207B |
S2140002A0D7890024D78A0028D78B002CD78C00301B |
S2140002B0D78D0034D78E0038D78F003CD7900040BB |
S2140002C0D7910044D7920048D793004CD79400505B |
S2140002D0D7950054D7960058D797005CD7980060FB |
S2140002E0D7990064D79A0068D79B006CD79C00709B |
S2140002F0D79D0074D79E0078D79F007CE00800004A |
S214000300D7880080E0080001D7880084E008000253 |
S214000310D7880088E0080003D788008CABFFFF99D9 |
S2140003200FBD0020D7B70010D7BF00147C01C3FF55 |
S2140003304C21C00900012000B0001901B000088758 |
S2140003407C01C00000012000B0001007A8000009D2 |
S2140003507C01C3FF4C21C00000012000B000134107 |
S2140003600002B80000172000B00014180017200084 |
S214000370B000084FABFFFFF600001000C3B7001038 |
S214000380C3BF001407BD0020AFE000000FBD002073 |
S214000390D7BF00107C01C3FF4C21CF4A00012000CC |
S2140003A0B00018E77C01C3FF4C21CF3600012000C7 |
S2140003B0B00018E37C01C3FF4C21CF1A00012000D7 |
S2140003C0B00018DF7C01C3FF4C21CF0600012000DF |
S2140003D0B00018DB7C01C3FF4C21CEF000012000EA |
S2140003E0B00018D77C01C3FF4C21CED000012000FE |
S2140003F0B00018D37C01C3FF4C21CEAC0001200016 |
S214000400B00018CF7C01C3FF4C21CE950001200020 |
S214000410B00018CB7C01C3FF4C21CE7E000120002B |
S214000420B00018C77C01C3FF4C21CE660001200037 |
S214000430B00018C37C01C3FF4C21CE490001200048 |
S214000440B00018BF7C01C3FF4C21CE320001200053 |
S214000450B00018BB7C01C3FF4C21CE120001200067 |
S214000460B00018B77C01C3FF4C21CDEE0001200080 |
S214000470B00018B37C01C3FF4C21CDCE0001200094 |
S214000480B00018AF7C01C3FF4C21CDAD00012000A9 |
S214000490B00018AB7C01C3FF4C21CD8C00012000BE |
S2140004A0B00018A77C01C3FF4C21CD6D00012000D1 |
S2140004B0B00018A37C01C3FF4C21CD4400012000EE |
S2140004C0B000189FC3BF001007BD0020AFE00000BB |
S2140004D00FBD0020D7BF00107C01C3FF4C21CD17F5 |
S2140004E000012000B00018967C01C3FF4C21CCEE22 |
S2140004F000012000B0001892C3BF001007BD002006 |
S214000500AFE000000FBD0020D7BF00107C01C3FF86 |
S2140005104C21CCB600012000B0001889C3BF0010E3 |
S21400052007BD0020AFE000000FBD0020D7BF0010C1 |
S2140005307C01C3FF4C21CC8900012000B00018804C |
S2140005407C01C3FF4C21CC5800012000B000187C71 |
S214000550C3BF001007BD0020AFE000000FBD0020A5 |
S214000560D7BF00107C01C3FF4C21CC1F0001200028 |
S214000570B00018737C01C3FF4C21CBE200012000C1 |
S214000580B000186F7C01C3FF4C21CBA200012000F5 |
S214000590B000186BC3BF001007BD0020AFE000001E |
S2140005A00FBD0020D7BF00107C01C3FF4C21CB81BC |
S2140005B000012000B00018627C01C3FF4C21CB581C |
S2140005C000012000B000185EC3BF001007BD002069 |
S2140005D0AFE000000FBD0020D7BF00107C01C3FFB6 |
S2140005E04C21CB3000012000B00018557C01C3FF21 |
S2140005F04C21CAFC00012000B0001851C3BF0010F7 |
S21400060007BD0020AFE000000FBD0020D7BF0010E0 |
S2140006107C01C3FF4C21CACB00012000B000184863 |
S2140006207C01C3FF4C21CA9700012000B00018448B |
S214000630C3BF001007BD0020AFE000000FBD0020C4 |
S214000640D7BF00107C01C3FF4C21CA7A00012000EE |
S214000650B000183B7C01C3FF4C21CA5400012000A7 |
S214000660B0001837C3BF001007BD0020AFE0000081 |
S2140006700FBD0020D7BF00107C01C3FF4C21CA3637 |
S21400068000012000B000182E7C01C3FF4C21CA0FC9 |
S21400069000012000B000182AC3BF001007BD0020CC |
S2140006A0AFE000000FBD0020D7BF00107C01C3FFE5 |
S2140006B04C21C9E700012000B00018217C01C3FFCF |
S2140006C04C21C9BE00012000B000181D7C01C3FFEC |
S2140006D04C21C98C00012000B0001819C3BF0010BF |
S2140006E007BD0020AFE000000FBD0020D7BF001000 |
S2140006F07C01C3FF4C21C95900012000B00018102E |
S2140007007C01C3FF4C21C92200012000B000180C58 |
S2140007107C01C3FF4C21C8E900012000B000180886 |
S214000720C3BF001007BD0020AFE000000FBD0020D3 |
S214000730D7BF00107C01C3FF4C21C8BD00012000BC |
S214000740B00017FF7C01C3FF4C21C88D00012000BC |
S214000750B00017FB7C01C3FF4C21C85400012000E9 |
S214000760B00017F7C3BF001007BD0020AFE00000C1 |
S2140007700FBD0020D7BF00107C01C3FF4C21C8244A |
S21400078000012000B00017EE7C01C3FF4C21C7F02B |
S21400079000012000B00017EA7C01C3FF4C21C7B35C |
S2140007A000012000B00017E6C3BF001007BD002000 |
S2140007B0AFE000000FBD0020D7BF00107C01C3FFD4 |
S2140007C04C21C78700012000B00017DD7C01C3FF65 |
S2140007D04C21C75700012000B00017D97C01C3FF89 |
S2140007E04C21C71E00012000B00017D5C3BF001063 |
S2140007F007BD0020AFE000000FBD0020D7BF0010EF |
S2140008007C01C3FF4C21C6F700012000B00017CCC6 |
S2140008107C01C3FF4C21C6C900012000B00017C8E8 |
S2140008207C01C3FF4C21C68D00012000B00017C418 |
S2140008307C01C3FF4C21C65000012000B00017C049 |
S214000840C3BF001007BD0020AFE000000FBD0020B2 |
S214000850D7BF00107C01C3FF4C21C610000120004A |
S214000860B00017B7C3BF001007BD0020AFE0000000 |
S2140008700FBD0020D7BF00107C01C3FF4C21C5D19F |
S21400088000012000B00017AEC3BF001007BD002057 |
S214000890AFE000000FBD0020D7B70010D7BF001490 |
S2140008A0D7A40020D7A50024C3A4002007A5001CB9 |
S2140008B004060010B00013FDC3AF0024D5E200000C |
S2140008C0C3B8001CCF180000870000020417000100 |
S2140008D0A80000010000B80000171000C3B7001001 |
S2140008E0C3BF001407BD0020AFE000000FBD00200E |
S2140008F0D7B70010D7BF0014D7A40020D7A5002470 |
S214000900C3A4002007A5001C0406000AB00013E7D5 |
S214000910C3AF00240002C000D5F80000C3B8001C16 |
S214000920CF1800008700000204170001A80000018D |
S2140009300000B80000171000C3B70010C3BF0014B3 |
S21400094007BD0020AFE000000FBD0020D7B60010A6 |
S214000950D7B70014D7BF0018B0000E7E0002B8004C |
S214000960B0000E97D7A2001C00172000B00011445C |
S2140009700002B0000016200000172800B0000BA8E8 |
S2140009800002C0007C01C3FF4C21C5B1000120005D |
S214000990001728000016300000183800B00017684E |
S2140009A0C3B60010C3B70014C3BF001807BD0020AD |
S2140009B0AFE000000FBD0020D7BF0010B0000E8FC4 |
S2140009C0D7A2001C7C01C3FF4C21C5AB0001200050 |
S2140009D0B000175BB0000E84804000067C01C3FFA9 |
S2140009E04C21C5A600012000C3A5001CB00017546A |
S2140009F0A80000047C01C3FF4C21C59D0001200017 |
S214000A00B000174F7C01C3FF4C21C59B000120009E |
S214000A10B000174BC3BF001007BD0020AFE00000BA |
S214000A200FBD0020D7B50010D7B60014D7B70018F2 |
S214000A30D7BF001CB0000E620002B0007C01C3FFEE |
S214000A404C21C57600012000B000173D7C01C3FF95 |
S214000A504C21C57000012000B00017390417001F94 |
S214000A600418001B82F800080418001A82F8000612 |
S214000A700418001782F800040418001482F8000214 |
S214000A800418000F86F800047C01C3FF4C21C56DD6 |
S214000A9000012000B000172A7C01C3FF4C21C56A64 |
S214000AA000012000041800016317C00042D8C000EF |
S214000AB08300000204150031A80000010415003070 |
S214000AC000152800B000171E0EF700019AE0FFE49C |
S214000AD07C01C3FF4C21C59B00012000B000171805 |
S214000AE0C3B50010C3B60014C3B70018C3BF001CBC |
S214000AF007BD0020AFE000000FBD0020D7B70010F4 |
S214000B00D7BF0014D7A40020D7A50024C3B800245C |
S214000B10040F0001870F0002B3FFFE1CA80000258B |
S214000B20C3B80024040F0002870F00210000B8009D |
S214000B30A80000130418000C1317C0007C01C3FFA4 |
S214000B404C21C02800380800C0240000C3B800208C |
S214000B50C3050004B0001264844000080418000CAA |
S214000B601317C0007C01C3FF4C21C02C00380800BE |
S214000B70C0390000B7200000A800000E06F70001EC |
S214000B807C01C3FF4C21C0F400200800C0380000E0 |
S214000B9092F8FFE87C01C3FF4C21C5470001200006 |
S214000BA0C3B80020C3050004B00016E5A800000185 |
S214000BB0B3FFFE47C3B70010C3BF001407BD002035 |
S214000BC0AFE000000FBD0030D7BF0010D7A4003044 |
S214000BD0D7A50034C3B80034040F0003870F0021E4 |
S214000BE0C3B80030C304000407A5002CB3FFFF29D8 |
S214000BF0844000057C01C3FF4C21C5310001200064 |
S214000C00B00016CFA8000018C3B80030C304000810 |
S214000C1007A50028B3FFFF1F844000057C01C3FF23 |
S214000C204C21C51A00012000B00016C5A800000E11 |
S214000C30C3B8002CC3AF0028030F7000D7AE002443 |
S214000C400B0FC000D7B800207C01C3FF4C21C502A3 |
S214000C5000012000C3A50024C3A60020B00016B8DB |
S214000C60A8000001B3FFFE27C3BF001007BD003079 |
S214000C70AFE000000FBD0050D7B60010D7B7001485 |
S214000C80D7BF0018D7A40050D7A50054C3B8005447 |
S214000C90040F0001870F0003B0000DAED7A2004C72 |
S214000CA0A800000FC3B80054040F0002870F000A04 |
S214000CB0C3B80050C304000407A5004CB3FFFEF5FC |
S214000CC0844000077C01C3FF4C21C4F100012000D2 |
S214000CD0B000169BA800002EB3FFFE13A800002C41 |
S214000CE0C3B8004C7C01FFFF4C21FFFC4301C00051 |
S214000CF0D7B8004CB0000DB2D7A20024A80000233D |
S214000D0007A4002E7C01C3FF4C21C4E40001280088 |
S214000D10C3A6004CB00016B307A4002EB00010D136 |
S214000D200002B800CEF8000083000002040F000A9C |
S214000D30870F0001A800001600172000B00011A3BE |
S214000D4000172000C3A5004C07A60028B00006AF79 |
S214000D500002B0000016C000830000067C01C3FF3E |
S214000D604C21C4E00001200000162800B0001674D4 |
S214000D70A8000006C3A4004CC3A50028B000104974 |
S214000D80C3B8004C07180004D7B8004CABFFFFDC14 |
S214000D90C3B60010C3B70014C3BF001807BD005089 |
S214000DA0AFE000000FBD0030D7B60010D7B7001474 |
S214000DB0D7BF0018D7A40030D7A50034C3B8003476 |
S214000DC0040F0001870F0005B0000D62D7A2002CAB |
S214000DD004180010D7B80028A800002CC3B80034A8 |
S214000DE0040F0002870F000DC3B80030C3040004D0 |
S214000DF007A5002CB3FFFEA7844000057C01C3FFB7 |
S214000E004C21C4F100012000B000164DA80000419E |
S214000E1004180010D7B80028A800001CC3B8003477 |
S214000E20040F0003870F0017C3B80030C304000484 |
S214000E3007A5002CB3FFFE97844000057C01C3FF86 |
S214000E404C21C4F100012000B000163DA80000317E |
S214000E50C3B80030C304000807A50028B3FFFE8D02 |
S214000E60844000057C01C3FF4C21C4D10001200052 |
S214000E70B0001633A8000027C3B800288700000378 |
S214000E80A8000024B3FFFDB5A8000022C3B8002CBC |
S214000E907C01FFFF4C21FFFC4301C000D7B8002CAB |
S214000EA0B0000D47D7A200240000B000A80000162E |
S214000EB0C3A4002CB0000FF20002B80000172000F8 |
S214000EC0C3A5002CB0000A560002C0007C01C3FF78 |
S214000ED04C21C4BE00012000C3A5002C0017300022 |
S214000EE000183800B0001616C3B8002C070F000410 |
S214000EF09DF80001A8000007C3B8002C07180004DE |
S214000F00D7B8002C06D600010016C000C3AF0028D4 |
S214000F10970FFFE7C3B60010C3B70014C3BF00188F |
S214000F2007BD0030AFE000000FBD0020D7BF0010A7 |
S214000F30D7A40020D7A50024C3B80024040F0001BE |
S214000F40870F0003B0000D3CB3FFFE9AA800001701 |
S214000F50C3B80024040F0002870F0013C3B8002094 |
S214000F60C304000407A5001CB3FFFE4A8440000526 |
S214000F707C01C3FF4C21C4F100012000B00015F035 |
S214000F80A800000AC3B8001C7C01FFFF4C21FFFC30 |
S214000F904301C000D7B8001CC3A4001CB0000D1C41 |
S214000FA0B3FFFE84A8000001B3FFFD7DC3BF0010A1 |
S214000FB007BD0020AFE000000FBD0020D7B700102F |
S214000FC0D7BF0014D7A40020D7A50024C3B8002498 |
S214000FD0040F0001870F000304180001D7B8001C97 |
S214000FE0A8000011C3B80024040F0002870F000CED |
S214000FF0C3B80020C304000407A5001CB3FFFE25E9 |
S21400100080400002C3B8001C870000077C01C3FFB5 |
S2140010104C21C4D100012000B00015C9A800001062 |
S214001020B3FFFD6CA800000E0000B800A800000288 |
S214001030B0000E9D06F70001C3B8001C96F8FFFC32 |
S214001040B0000CC4D7A200187C01C3FF4C21C4AF6B |
S21400105000012000C3A50018B00015B9B3FFFE3A82 |
S214001060C3B70010C3BF001407BD0020AFE00000E8 |
S2140010700FBD0020D7B70010D7BF0014D7A400209C |
S214001080D7A50024C3B80024040F0001870F00036F |
S21400109004180001D7B8001CA8000011C3B800242B |
S2140010A0040F0002870F000CC3B80020C30400041E |
S2140010B007A5001CB3FFFDF780400002C3B8001C64 |
S2140010C0870000077C01C3FF4C21C4D1000120002B |
S2140010D0B000159BA8000009B3FFFD4BA800000751 |
S2140010E00000B800A8000002B0000D3006F70001AE |
S2140010F0C3B8001C96F8FFFCB3FFFE13C3B700107E |
S214001100C3BF001407BD0020AFE000000FBD0020E5 |
S214001110D7BF0010D7A40020D7A50024C3B800244A |
S214001120040F0001870F0002B3FFFE07A800001798 |
S214001130C3B80024040F0002870F0013C3B80020B2 |
S214001140C304000407A5001CB3FFFDD284400005BD |
S2140011507C01C3FF4C21C4F100012000B0001578CB |
S214001160A800000AC3B8001C7C01FFFF4C21FFFC4E |
S2140011704301C000D7B8001CC3A4001CB0000C7A02 |
S214001180B3FFFDF1A8000001B3FFFD2CC3BF0010A4 |
S21400119007BD0020AFE000000FBD0060D7B0001014 |
S2140011A0D7B10014D7B20018D7B3001CD7B40020AC |
S2140011B0D7B50024D7B60028D7B7002CD7BF003045 |
S2140011C00004B8007C01C3FF4C21C481000120004C |
S2140011D07C01080042E1C000830000047C01C3FFDC |
S2140011E04C21C47D0001A800A80000037C01C3FFB9 |
S2140011F04C21C4790001A800001528007C010800D5 |
S21400120042E1C000830000047C01C3FF4C21C4758A |
S2140012100001A000A80000037C01C3FF4C21C4719C |
S2140012200001A00000143000B00015457C01C3FF8B |
S2140012304C21C443000120007C01040042E1C000B0 |
S214001240830000047C01C3FF4C21C47D000198008C |
S214001250A80000037C01C3FF4C21C479000198005C |
S214001260001328007C01040042E1C0008300000453 |
S2140012707C01C3FF4C21C43E00019000A80000037F |
S2140012807C01C3FF4C21C4370001900000123000DF |
S214001290B000152B7C01C3FF4C21C40900012000BF |
S2140012A07C01020042E1C000830000047C01C3FF11 |
S2140012B04C21C47D00018800A80000037C01C3FF08 |
S2140012C04C21C47900018800001128007C0102002E |
S2140012D042E1C000830000047C01C3FF4C21C43EF1 |
S2140012E000018000A80000037C01C3FF4C21C43726 |
S2140012F00001800000103000B00015117C01C3FF13 |
S2140013004C21C3DB000120007C01010042E1C0004B |
S214001310830000057C01C3FF4C21C47D0001C00092 |
S214001320D7B8005CA80000047C01C3FF4C21C47938 |
S2140013300001C000D7B8005CC3A5005C7C010100BA |
S21400134042E1C000830000057C01C3FF4C21C43E7F |
S2140013500001C000D7B80058A80000047C01C3FFF5 |
S2140013604C21C4370001C000D7B80058C3A60058A7 |
S214001370B00014F37C01C3FF4C21C3AD0001200074 |
S2140013807C01008042E1C000830000057C01C3FFB1 |
S2140013904C21C47D0001C000D7B80054A80000044A |
S2140013A07C01C3FF4C21C4790001C000D7B80054AB |
S2140013B0C3A500547C01008042E1C0008300000504 |
S2140013C07C01C3FF4C21C3A50001C000D7B8005064 |
S2140013D0A80000047C01C3FF4C21C39C0001C00090 |
S2140013E0D7B80050C3A60050B00014D57C01C3FF88 |
S2140013F04C21C36E000120007C01004042E1C00089 |
S214001400830000057C01C3FF4C21C47D0001C000A1 |
S214001410D7B8004CA80000047C01C3FF4C21C47957 |
S2140014200001C000D7B8004CC3A5004C7C010040AA |
S21400143042E1C000830000057C01C3FF4C21C3A528 |
S2140014400001C000D7B80048A80000047C01C3FF14 |
S2140014504C21C39C0001C000D7B80048C3A6004872 |
S214001460B00014B77C01C3FF4C21C340000120002C |
S2140014707C01002042E1C000830000057C01C3FF20 |
S2140014804C21C47D0001C000D7B80044A800000469 |
S2140014907C01C3FF4C21C4790001C000D7B80044CA |
S2140014A0C3A500447C01002042E1C0008300000583 |
S2140014B07C01C3FF4C21C3A50001C000D7B8004083 |
S2140014C0A80000047C01C3FF4C21C39C0001C0009F |
S2140014D0D7B80040C3A60040B00014997C01001F96 |
S2140014E042E1C0006F18001000182000B0000BD7B3 |
S2140014F00002C0007C01C3FF4C21C30F0001200086 |
S2140015007C01001F42E178006DE5001000183000F5 |
S214001510B000148B0416000F00162000B0000BCB92 |
S2140015207C01C3FF4C21C2FF0001200000022800FE |
S214001530041800016316C00042F8C00083000005CE |
S2140015407C01C3FF4C21C47D0001C000D7B8003C1D |
S214001550A80000047C01C3FF4C21C4790001C00030 |
S214001560D7B8003CC3A6003C041800016316C000B0 |
S21400157042F8C000830000057C01C3FF4C21C3A5D0 |
S2140015800001C000D7B80038A80000047C01C3FFE3 |
S2140015904C21C39C0001C000D7B80038C3A7003850 |
S2140015A0B00014670ED600019AC0FFDBC3B000106F |
S2140015B0C3B10014C3B20018C3B3001CC3B40020E8 |
S2140015C0C3B50024C3B60028C3B7002CC3BF003081 |
S2140015D007BD0060AFE000000FBD0020D7BF0010C1 |
S2140015E0D7A40020D7A50024C3B80024040F000108 |
S2140015F0870F0006B0000B72D7A2001CB3FFFD08D1 |
S214001600C3A4001CB3FFFEE4A8000019C3B800245E |
S214001610040F0002870F0015C3B80020C30400049F |
S21400162007A5001CB3FFFC9B844000057C01C3FF9C |
S2140016304C21C2F100012000B0001441A800000CAB |
S214001640C3B8001C7C010FFF4C21FFFF4301C00004 |
S214001650D7B8001CC3A4001CB0000B5EB3FFFCF0A0 |
S214001660C3A4001CB3FFFECCA8000001B3FFFC001F |
S214001670C3BF001007BD0020AFE000000FBD003064 |
S214001680D7B60010D7B70014D7BF0018D7A40030BD |
S214001690D7A50034C3B80034040F0001870F001C20 |
S2140016A00000B0000000B80066F800030316C00093 |
S2140016B0D7B8002CC3A4002CB0000B30D7A200284B |
S2140016C07C01C3FF4C21C2E000012000C3A5002C12 |
S2140016D0C3A60028B000141A06F700010418000478 |
S2140016E092F8FFF17C01C3FF4C21C59B000120004E |
S2140016F0B000141306D600010418000892D8FFE9BB |
S214001700B3FFFCC7B3FFFCABB3FFFC8FA800003BE6 |
S214001710C3B80034040F0002870F0018C3B80030A7 |
S214001720C304000407A5002CB3FFFC70804000042F |
S214001730C3B8002C93000002040F0020930F00058E |
S2140017407C01C3FF4C21C2C700012000B00013FC7F |
S214001750A800002AC3A4002CB0000B08D7A20028BB |
S2140017607C01C3FF4C21C2BA00012000C3A5002C97 |
S214001770C3A60028B00013F2A8000020C3B80034A7 |
S214001780040F0003870F001CC3B80030C304000416 |
S21400179007A5002CB3FFFC5580400004C3B8002CFE |
S2140017A093000002040F0020930F00057C01C3FF86 |
S2140017B04C21C2C700012000B00013E1A800000FB2 |
S2140017C0C3B80030C304000807A50028B3FFFC31E7 |
S2140017D0844000057C01C3FF4C21C2F100012000BB |
S2140017E0B00013D7A8000005C3A4002CC3A500288A |
S2140017F0B0000AE9A8000001B3FFFBAAC3B60010B8 |
S214001800C3B70014C3BF001807BD0030AFE0000028 |
S2140018100FBD0040D7B00010D7B10014D7B20018E3 |
S214001820D7B3001CD7B40020D7B50024D7B60028FD |
S214001830D7B7002CD7BF0030D7A40040D7A50044A8 |
S214001840C3B80044040F0001870F0005B0000AC1AA |
S214001850D7A2003C04180100D7B80038A800002C16 |
S214001860C3B80044040F0002870F000DC3B8004041 |
S214001870C304000407A5003CB3FFFC068440000533 |
S2140018807C01C3FF4C21C4F100012000B00013AC62 |
S214001890A800007D04180100D7B80038A800001C76 |
S2140018A0C3B80044040F0003870F0017C3B80040F6 |
S2140018B0C304000407A5003CB3FFFBF68440000504 |
S2140018C07C01C3FF4C21C4F100012000B000139C32 |
S2140018D0A800006DC3B80040C304000807A5003880 |
S2140018E0B3FFFBEC844000057C01C3FF4C21C4D150 |
S2140018F000012000B0001392A8000063C3B80038AF |
S21400190087000003A8000060B3FFFB77A800005E16 |
S214001910B0000AABD7A20034C3B8003C7C01FFFF7E |
S2140019204C21FFF043018000C3AF0038030FC00016 |
S2140019300F1300019E7000010413FFFF0A70C00021 |
S214001940071800106F180004001888000010A00088 |
S21400195000009000A800004B7C01C3FF4C21C2B2DF |
S2140019600001200000142800B00013750000B0002D |
S2140019700016C0000298B800C3B8003C96F80001F4 |
S2140019808EF300057C01C3FF4C21C56D00012000CD |
S214001990B000136BA800000900172000B0000D3E31 |
S2140019A00002C0000018A8007C01C3FF4C21C2AD95 |
S2140019B00001200046A500FFB00013617C01C3FFB4 |
S2140019C04C21C2AB00012000B000135D06D600011A |
S2140019D00418001092D8FFE67C01C3FF4C21C56DA9 |
S2140019E000012000B00013560000B0000016C00032 |
S2140019F00298B800C3B8003C96F800018EF30005C4 |
S214001A007C01C3FF4C21C2AB00012000B000134C88 |
S214001A10A800001300172000B0000D1F0002C00031 |
S214001A200018A80046B800FF040F0020930F000817 |
S214001A30040F007EA30F00067C01C3FF4C21C56A7D |
S214001A400001200046A500FFB000133DA8000004DA |
S214001A507C01C3FF4C21C2A900012000B00013384E |
S214001A6006D600010418001092D8FFE07C01C3FFE0 |
S214001A704C21C59B00012000B000133106940010D5 |
S214001A80065200019251FFB4C3B00010C3B1001457 |
S214001A90C3B20018C3B3001CC3B40020C3B50024EF |
S214001AA0C3B60028C3B7002CC3BF003007BD004034 |
S214001AB0AFE000000FBD0030D7BF0010D7A4003045 |
S214001AC0D7A50034B0000A3ED7A20024C3B800341D |
S214001AD0040F0001870F000CB0000A1ED7A2002CCE |
S214001AE0C3A4002CB0000CE6D7A200287C01C3FFDC |
S214001AF04C21C29C00012000C3A5002CC3A60028D0 |
S214001B00B000130FA8000035C3B80034040F00025D |
S214001B10870F0014C3B80030C304000407A5002CC8 |
S214001B20B3FFFB5C844000057C01C3FF4C21C4F17D |
S214001B3000012000B0001302A8000028C3A4002C57 |
S214001B40B0000CCFD7A200287C01C3FF4C21C29C5A |
S214001B5000012000C3A5002CC3A60028B00012F880 |
S214001B60A800001EC3B80034040F0003870F001A35 |
S214001B70C3B80030C304000407A5002CB3FFFB4520 |
S214001B80844000057C01C3FF4C21C4F10001200005 |
S214001B90B00012EBA8000011C3B80030C304000860 |
S214001BA007A50020B3FFFB3B844000057C01C3FF74 |
S214001BB04C21C2F100012000B00012E1A80000078D |
S214001BC0C3B80020D7B80028C3A4002CC3A500289B |
S214001BD0B0000CB4A8000001B3FFFAD4C3BF0010D5 |
S214001BE007BD0030AFE000000FBD0030D7BF0010CB |
S214001BF0D7A40030D7A50034B00009F1D7A200243E |
S214001C00C3B80034040F0001870F000DB00009D1DF |
S214001C10D7A2002CC3A4002CB0000C9C0002C0006D |
S214001C20DBB8002A7C01C3FF4C21C28F00012000D4 |
S214001C30C3A5002CCBA6002AB00012C1A80000360F |
S214001C40C3B80034040F0002870F0015C3B8003075 |
S214001C50C304000407A5002CB3FFFB0E8440000558 |
S214001C607C01C3FF4C21C4F100012000B00012B477 |
S214001C70A8000029C3A4002CB0000C840002C000F9 |
S214001C80DBB8002A7C01C3FF4C21C28F0001200074 |
S214001C90C3A5002CCBA6002AB00012A9A800001EDF |
S214001CA0C3B80034040F0003870F001AC3B800300F |
S214001CB0C304000407A5002CB3FFFAF68440000511 |
S214001CC07C01C3FF4C21C4F100012000B000129C2F |
S214001CD0A8000011C3B80030C304000807A5002000 |
S214001CE0B3FFFAEC844000057C01C3FF4C21C2F12F |
S214001CF000012000B0001292A8000007C3B8002020 |
S214001D00DBB8002AC3A4002CCBA5002AB0000C68C0 |
S214001D10A8000001B3FFFA96C3BF001007BD00304D |
S214001D20AFE000000FBD0030D7BF0010D7A40030D2 |
S214001D30D7A50034B00009A2D7A20024C3B8003447 |
S214001D40040F0001870F000DB0000982D7A2002CF7 |
S214001D50C3A4002CB0000C500002C000DFB8002B5B |
S214001D607C01C3FF4C21C28200012000C3A5002CC9 |
S214001D70D3A6002BB0001272A8000036C3B80034F9 |
S214001D80040F0002870F0015C3B80030C304000418 |
S214001D9007A5002CB3FFFABF844000057C01C3FFF3 |
S214001DA04C21C4F100012000B0001265A8000029F3 |
S214001DB0C3A4002CB0000C380002C000DFB8002B13 |
S214001DC07C01C3FF4C21C28200012000C3A5002C69 |
S214001DD0D3A6002BB000125AA800001EC3B80034C9 |
S214001DE0040F0003870F001AC3B80030C3040004B2 |
S214001DF007A5002CB3FFFAA7844000057C01C3FFAB |
S214001E004C21C4F100012000B000124DA8000011C2 |
S214001E10C3B80030C304000807A50020B3FFFA9D2E |
S214001E20844000057C01C3FF4C21C2F10001200064 |
S214001E30B0001243A8000007C3B80020DFB8002B8C |
S214001E40C3A4002CD3A5002BB0000C1CA8000001D6 |
S214001E50B3FFFA58C3BF001007BD0030AFE0000064 |
S214001E600FBD0040D7B60018D7B7001CD7BF00205C |
S214001E70D7A40040D7A50044C3B80044040F00010F |
S214001E80870F0033D7A0002C07A40030C3A5002C72 |
S214001E90B0000C2B7C01C3FF4C21C2520001200075 |
S214001EA0C3A5002CC3A60030C3A70034C3B80038AF |
S214001EB08300000204170077A80000010417002D15 |
S214001EC0D7B70010C3B8003C8300000204160076A3 |
S214001ED0A80000010416002DD7B60014B000121892 |
S214001EE0C3B8002C07180001D7B8002CC3B8002CC4 |
S214001EF0040F0020930FFFE4B0000BF30002C000B5 |
S214001F007C01C3FF4C21C2410001200000182800BC |
S214001F10B000120BB0000BF60002C0007C01C3FF3D |
S214001F204C21C2300001200000182800B000120426 |
S214001F30B0000BF90002C0007C01C3FF4C21C21F99 |
S214001F400001200000182800B00011FDA800009B2A |
S214001F50C3B80044040F0002870F0025C3B8004032 |
S214001F60C304000407A5002CB3FFFA6080400004F9 |
S214001F70C3B8002C93000002040F0020930F000546 |
S214001F807C01C3FF4C21C20C00012000B00011EC04 |
S214001F90A800008A07A40030C3A5002CB0000BE8F8 |
S214001FA07C01C3FF4C21C25200012000C3A5002CB7 |
S214001FB0C3A60030C3A70034C3B8003883000002AD |
S214001FC004170077A80000010417002DD7B70010EB |
S214001FD0C3B8003C8300000204160076A800000187 |
S214001FE00416002DD7B60014B00011D5A800007353 |
S214001FF0C3B80044040F0003870F0002B3FFF9FEC6 |
S214002000A800006EC3B80044040F0004870F006ADF |
S214002010C3B80040C304000407A5002CB3FFFA337E |
S21400202080400004C3B8002C93000002040F002078 |
S214002030930F00057C01C3FF4C21C20C0001200059 |
S214002040B00011BFA800005DC3B80040C304000C78 |
S21400205007A50028B3FFFA0F844000057C01C3FFE4 |
S2140020604C21C2F100012000B00011B5A8000053B9 |
S21400207007A40030C3A5002CB0000BB1C3B80040C5 |
S214002080C30400087C01C3FF4C21C20A00012800DB |
S214002090B0000D1584400006C3B800287C01FFFF81 |
S2140020A04C21F0004301C000D7B80030A800002043 |
S2140020B0C3B80040C30400087C01C3FF4C21C2081B |
S2140020C000012800B0000D0884400014C3B80028A2 |
S2140020D07C01FFFF4C21F0004301C000D7B800345C |
S2140020E0C3B8002847180002830000020417000146 |
S2140020F0A80000010000B800D7B70038C3B8002811 |
S214002100471800018300000204160001A800000121 |
S2140021100000B000D7B6003CA80000057C01C3FF55 |
S2140021204C21C1E100012000B0001185A800002369 |
S214002130C3A4002C07A80030C1030000C109000496 |
S214002140D7A30004D7A90008C1030008C109000CE2 |
S214002150D7A3000CD7A90010C3A50004C3A6000887 |
S214002160C3A7000CB0000BA87C01C3FF4C21C252D1 |
S21400217000012000C3A5002CC3A60030C3A700346E |
S214002180C3B800388300000204170077A8000001D7 |
S2140021900417002DD7B70010C3B8003C8300000218 |
S2140021A004160076A80000010416002DD7B6001409 |
S2140021B0B0001163A8000001B3FFF98FC3B6001882 |
S2140021C0C3B7001CC3BF002007BD0040AFE000003F |
S2140021D00FBD0020D7BF0010D7A40020D7A500242D |
S2140021E0C3B80024040F0002870F0011C3B80020F4 |
S2140021F0C304000407A5001CB3FFF9BC804000041C |
S214002200C3B8001C93000002040F00018B0F0005EA |
S2140022107C01C3FF4C21C1C500012000B00011485D |
S214002220A8000004C3A4001CB00006A3A800000178 |
S214002230B3FFF986C3BF001007BD0020AFE0000063 |
S2140022400FBD0020D7BF0010D7A40020D7A50024BC |
S214002250C3B80024040F0002870F0011C3B8002083 |
S214002260C304000407A5001CB3FFF9A080400004C7 |
S214002270C3B8001C93000002040F00018B0F00057A |
S2140022807C01C3FF4C21C1B000012000B000112C1E |
S214002290A8000004C3A4001CB00007E0A8000001CA |
S2140022A0B3FFF973C3BF001007BD0020AFE0000006 |
S2140022B00FBD0050D7B50010D7B60014D7B700181A |
S2140022C0D7BF001CD7A400500000A800C3A400502D |
S2140022D07C01C3FF4C21C18000012800B0000CBE69 |
S2140022E00002B000A80000130418000A86B8000513 |
S2140022F07C01C3FF4C21C16700012000B000111013 |
S214002300A800002C0015C000071500016718000281 |
S21400231007AF0028030FC000D716000000002000FB |
S2140023207C01C3FF4C21C18000012800B0000CAA2C |
S2140023300002B0000016C0008700FFEB86A0000178 |
S214002340A800001C0000B800A80000140418000C28 |
S2140023501317C0007C01C3FF4C21C02800380800BA |
S214002360C0240000C3A50028B0000C5F8440000A0B |
S21400237007A40028001528000418000C1317C00036 |
S2140023807C01C3FF4C21C03000380800C039000073 |
S214002390B7200000A800000706F700017C01C3FF75 |
S2140023A04C21C0F400200800C038000092F8FFE777 |
S2140023B0B3FFF7F6C3B50010C3B60014C3B70018D2 |
S2140023C0C3BF001C07BD0050AFE000000FBD0010EB |
S2140023D0D7B700006497001876F70018041800694D |
S2140023E082F8000DA2F800060418006182F8000AC0 |
S2140023F092F8000D0418006582F80007A800000A8D |
S2140024000418006F82F8000492F80007041800759C |
S21400241082F80001A80000047C01C3FF4C21C164BF |
S21400242000011000A80000037C01C3FF4C21C1621C |
S21400243000011000C3B7000007BD0010AFE00000A9 |
S2140024400FBD0020D7B70010D7BF0014D7A40020B8 |
S214002450C3A40020B00007FD0002B8007C01C3FF43 |
S2140024604C21C59B00012000B00010B5CEE4000052 |
S214002470B3FFFFD60002C0007C01C3FF4C21C12F72 |
S214002480000120000018280000173000B00010AC33 |
S2140024907C01C3FF4C21C0F800012000B00010A84A |
S2140024A0C3B70010C3BF001407BD0020AFE0000094 |
S2140024B00FBD0040D7BF0010D7A4004007A40018E7 |
S2140024C0B3FFF7248040000807B800187C01C3FF5C |
S2140024D04C21DA7000200800D4380000C3A4004065 |
S2140024E0B3FFFF73A80000097C01C3FF4C21DAF498 |
S2140024F000200800C03800007C01001F4301C00017 |
S2140025006F18001000182000B3FFFFCD7C01C3FF3A |
S2140025104C21DA7000200800D4200000C3BF001051 |
S21400252007BD0040AFE000000FBD0020D7BF001081 |
S214002530D7A40020D7A50024C3B80020C3040000F9 |
S214002540C3B80024C3050000B0000BE70002C000BB |
S214002550C3BF001007BD0020AFE000000FBD002085 |
S214002560D7B70010D7BF00147C01C3FF4C21CF6043 |
S214002570000120000405002E0406000C7C01E0008B |
S2140025804C21252800013800B0000D770000B80067 |
S21400259066F800027C01C3FF4C21DB0C0038080003 |
S2140025A0D420000006F700010418004092F8FFF857 |
S2140025B00000B800A800002B0418000C1317C00079 |
S2140025C07C01C3FF4C21CF6800380800D02F0000E4 |
S2140025D065EF00027C01C3FF4C21CF600301C00001 |
S2140025E07C01C3FF4C21DB0C002F0800D438000010 |
S2140025F00418000C1317C0007C01C3FF4C21CF64E5 |
S21400260000380800C02F0000040E000681EE000609 |
S2140026107C01C3FF4C21CF6400380800C03800009E |
S214002620040F0007870F000E0418000C1317C000D5 |
S2140026307C01C3FF4C21CF6800380800D02F000073 |
S21400264065EF00027C01C3FF4C21CF600301C00090 |
S2140026507C01C3FF4C21DB10002F0800D43800009B |
S21400266006F700010017C000040F002E970FFFD2D8 |
S214002670C3B70010C3BF001407BD0020AFE00000C2 |
S2140026800FBD0030D7B30010D7B40014D7B500186C |
S214002690D7B6001CD7B70020D7BF00240004B80068 |
S2140026A00000A0000413002DA80000160293C0002E |
S2140026B0271600020418000C1316C0007C01C3FF86 |
S2140026C04C21CF6000380800C02400000017280006 |
S2140026D0B0000B850002A80086A000060418000CB7 |
S2140026E01316C0007C01C3FF4C21CF60030110000D |
S2140026F0A80000069AA0000206D40001A800000167 |
S2140027000ED300018A93FFE900001000C3B3001047 |
S214002710C3B40014C3B50018C3B6001CC3B700206A |
S214002720C3BF002407BD0030AFE000000FBD00208F |
S214002730D7B70010D7BF0014D7A400200005B800F4 |
S214002740C3B80020CF180000040F0024830F000237 |
S21400275000001000A8000013C3B800200704000102 |
S21400276007A5001C0406000AB0000C500002C000BA |
S214002770D6F80000C3B8001CCF1800008300000283 |
S21400278000001000A8000007C2F800009300000236 |
S214002790040F0020930F000200001000A8000001A4 |
S2140027A004020001C3B70010C3BF001407BD002019 |
S2140027B0AFE000000FBD0020D7B70010D7BF001451 |
S2140027C0D7A40020D7A50024C3A4002007A5001C7A |
S2140027D004060010B0000C35C3AF0024D5E200009C |
S2140027E0C3B8001CCF1800008700000204170001C1 |
S2140027F0A80000010000B80000171000C3B70010C2 |
S214002800C3BF001407BD0020AFE000000FBD00707E |
S214002810D7B40010D7B50014D7B60018D7B7001C29 |
S214002820D7BF0020D7A40070D7A50074D7A600781D |
S2140028300000B000C3A400707C01C3FF4C21D2A8E6 |
S21400284000012800B0000B640002B800A8000013C6 |
S2140028500418000A86D800057C01C3FF4C21D2501C |
S21400286000200800C0220000A80002D70016C00002 |
S214002870071600016718000207AF0048030FC000E4 |
S214002880D7170000000020007C01C3FF4C21D2A80F |
S21400289000012800B0000B500002B8000017C0006E |
S2140028A08700FFEB86C000057C01C3FF4C21D25495 |
S2140028B000200800C0220000A80002C3C3A40048ED |
S2140028C0B3FFFF6F0002A8000015C00087000005D8 |
S2140028D07C01C3FF4C21D25800200800C022000013 |
S2140028E0A80002B9C2B40004928002AE0418000A1E |
S2140028F0A29802AC669800027C01C3FF4C21D27CF1 |
S21400290000380800C0380000AF00000004180002BD |
S2140029108AD800057C01C3FF4C21D2600020080045 |
S214002920C0220000A80002A8041800019AD80005DA |
S2140029307C01C3FF4C21D26400200800C0220000A6 |
S214002940A80002A10418000286D80009C3A4004CFF |
S21400295007A50038B3FFFF97844000067C01C3FF3D |
S2140029604C21D26C00200800C0220000A80002966D |
S214002970D7A00038D2B800086718001AC3AF0038CE |
S2140029807C0103FF4C21FFFF41E178004B0FC000A4 |
S214002990D7B80044A8000288041800038AD80005A7 |
S2140029A07C01C3FF4C21D26000200800C02200003A |
S2140029B0A8000285041800039AD800057C01C3FF0E |
S2140029C04C21D26400200800C0220000A800027E2D |
S2140029D0C3A4004C07A5003CB3FFFF548440000589 |
S2140029E07C01C3FF4C21D26800200800C0220000F2 |
S2140029F0A8000275C3A4005007A50038B3FFFF6DFA |
S214002A00844000057C01C3FF4C21D26C00200800E6 |
S214002A10C0220000A800026CC3B800387C01000188 |
S214002A2000017800970F00057C01C3FF4C21D2708F |
S214002A3000200800C0220000A8000263D2B80008E8 |
S214002A406718001AC3AF003C65EF00104B0FC000BC |
S214002A50C3AF003845EFFFFF4B0FC000D7B80044A8 |
S214002A60A8000255041800038AD800057C01C3FF9D |
S214002A704C21D26000200800C0220000A8000252AC |
S214002A80041800039AD800057C01C3FF4C21D264C9 |
S214002A9000200800C0220000A800024BC3A4004C7F |
S214002AA007A5003CB3FFFF21844000057C01C3FF5F |
S214002AB04C21D26800200800C0220000A800024274 |
S214002AC0C3A4005007A50038B3FFFF3A84400005B2 |
S214002AD07C01C3FF4C21D26C00200800C0220000FD |
S214002AE0A8000239C3B800386F180010D7B80038ED |
S214002AF0C3B800387C01000100017800970F00057C |
S214002B007C01C3FF4C21D27000200800C0220000C8 |
S214002B10A800022DD2B800086718001AC3AF003C00 |
S214002B2065EF00104B0FC000C3AF003845EFFFFF46 |
S214002B304B0FC000D7B80044A800021F04180004BA |
S214002B408AD800057C01C3FF4C21D2600020080013 |
S214002B50C0220000A800021C041800049AD8000531 |
S214002B607C01C3FF4C21D26400200800C022000074 |
S214002B70A8000215C3A4004C07A5003CB3FFFEEB5B |
S214002B80844000057C01C3FF4C21D2680020080069 |
S214002B90C0220000A800020CC3A4005007A5003401 |
S214002BA0B3FFFEE2844000057C01C3FF4C21D268DF |
S214002BB000200800C0220000A8000203C3A400549E |
S214002BC007A50038B3FFFEFB844000057C01C3FF69 |
S214002BD04C21D26C00200800C0220000A80001FA98 |
S214002BE0C3B800387C01000100017800970F00058B |
S214002BF07C01C3FF4C21D27000200800C0220000D8 |
S214002C00A80001F1D2B800086718001AC3AF003454 |
S214002C1065EF00154B0FC000C3AF003C65EF00101A |
S214002C204B0FC000C3AF003845EFFFFF4B0FC0008F |
S214002C30D7B80044A80001E0041800048AD80005AC |
S214002C407C01C3FF4C21D26000200800C022000097 |
S214002C50A80001DD041800049AD800057C01C3FF13 |
S214002C604C21D26400200800C0220000A80001D633 |
S214002C70C3A4004C07A5003CB3FFFEAC844000058F |
S214002C807C01C3FF4C21D26800200800C02200004F |
S214002C90A80001CDC3A4005007A50034B3FFFEA3CF |
S214002CA0844000057C01C3FF4C21D2680020080048 |
S214002CB0C0220000A80001C4C3A4005407A5004019 |
S214002CC0B3FFFEBC844000057C01C3FF4C21D26CE0 |
S214002CD000200800C0220000A80001BBC3B80040C6 |
S214002CE07C0100004C218000000178009B0F000250 |
S214002CF0040F80009B0F00057C01C3FF4C21D2709F |
S214002D0000200800C0220000A80001AFD2B80008CA |
S214002D106718001AC3AF003465EF00154B0FC000EC |
S214002D20C3AF003C65EF00104B0FC000C3AF0040C0 |
S214002D3045EFFFFF4B0FC000D7B80044A800019E28 |
S214002D40041800048AD800057C01C3FF4C21D26019 |
S214002D5000200800C0220000A800019B0418000400 |
S214002D609AD800057C01C3FF4C21D26400200800DD |
S214002D70C0220000A8000194C3A4004C07A5003C94 |
S214002D80B3FFFE6A844000057C01C3FF4C21D26875 |
S214002D9000200800C0220000A800018BC3A4005039 |
S214002DA007A50034B3FFFE61844000057C01C3FF25 |
S214002DB04C21D26800200800C0220000A800018232 |
S214002DC0C3A4005407A50030B3FFFE588440000596 |
S214002DD07C01C3FF4C21D26800200800C0220000FE |
S214002DE0A8000179D2B800086718001AC3AF0034EB |
S214002DF065EF00154B0FC000C3AF003065EF001045 |
S214002E004B0FC000C3AF003C65EF000B4B0FC0007C |
S214002E10D7B80044A8000168041800048AD8000542 |
S214002E207C01C3FF4C21D26000200800C0220000B5 |
S214002E30A8000165041800049AD800057C01C3FFA9 |
S214002E404C21D26400200800C0220000A800015EC9 |
S214002E50C3A4004C07A5003CB3FFFE348440000525 |
S214002E607C01C3FF4C21D26800200800C02200006D |
S214002E70A8000155C3A4005007A50034B3FFFE2BDD |
S214002E80844000057C01C3FF4C21D2680020080066 |
S214002E90C0220000A800014CC3B80054CF180000A0 |
S214002EA0040F0024870F0016C3A4005407A50030A3 |
S214002EB0B3FFFE1E844000057C01C3FF4C21D26890 |
S214002EC000200800C0220000A800013FD2B8000879 |
S214002ED06718001AC3AF003465EF00154B0FC0002B |
S214002EE0C3AF003065EF00104B0FC000C3AF003C0F |
S214002EF065EF000B4B0FC000D7B80044A800012EAA |
S214002F00C3A4005407A50038B3FFFE2A844000057A |
S214002F107C01C3FF4C21D26C00200800C0220000B8 |
S214002F20A8000129C3B800387C0100010001780020 |
S214002F30970F00057C01C3FF4C21D27000200800CB |
S214002F40C0220000A8000120D2B80008071800011F |
S214002F506718001AC3AF003465EF00154B0FC000AA |
S214002F60C3AF003C65EF00104B0FC000C3AF003886 |
S214002F7045EFFFFF4B0FC000D7B80044A800010E76 |
S214002F80041800048AD800057C01C3FF4C21D260D7 |
S214002F9000200800C0220000A800010B041800044E |
S214002FA09AD800057C01C3FF4C21D264002008009B |
S214002FB0C0220000A8000104C3A4004C07A5003CE2 |
S214002FC0B3FFFDDA844000057C01C3FF4C21D268C4 |
S214002FD000200800C0220000A80000FBC3A4005088 |
S214002FE007A50034B3FFFDD1844000057C01C3FF74 |
S214002FF04C21D26800200800C0220000A80000F281 |
S214003000C3B80054CF180000040F0024870F001622 |
S214003010C3A4005407A50030B3FFFDC484400005D8 |
S2140030207C01C3FF4C21D26800200800C0220000AB |
S214003030A80000E5D2B800086718001AC3AF00342D |
S21400304065EF00154B0FC000C3AF003065EF0010F2 |
S2140030504B0FC000C3AF003C65EF000B4B0FC0002A |
S214003060D7B80044A80000D4C3A4005407A5004065 |
S214003070B3FFFDD0844000057C01C3FF4C21D26C19 |
S21400308000200800C0220000A80000CFC3B80040FF |
S2140030907C0100004C218000000178009B0F00029C |
S2140030A0040F80009B0F00057C01C3FF4C21D270EB |
S2140030B000200800C0220000A80000C3D2B8000804 |
S2140030C0071800016718001AC3AF003465EF001533 |
S2140030D04B0FC000C3AF003C65EF00104B0FC000A5 |
S2140030E0C3AF004045EFFFFF4B0FC000D7B800440A |
S2140030F0A80000B1041800048AD800057C01C3FFAC |
S2140031004C21D26000200800C0220000A80000AEBB |
S214003110041800049AD800057C01C3FF4C21D26431 |
S21400312000200800C0220000A80000A7C3A4004C8E |
S21400313007A5003CB3FFFD7D844000057C01C3FF6E |
S2140031404C21D26800200800C0220000A800009E83 |
S214003150C3A4005007A50034B3FFFD7484400005E7 |
S2140031607C01C3FF4C21D26800200800C02200006A |
S214003170A8000095C3A4005407A50040B3FFFD8D2A |
S214003180844000057C01C3FF4C21D26C002008005F |
S214003190C0220000A800008CC3B8004047180003F7 |
S2140031A0830000057C01C3FF4C21D2740020080078 |
S2140031B0C0220000A8000084C3B80040C3AF00745B |
S2140031C005EF00040B0FC000D7B80040C3B800409E |
S2140031D027180004D7B80040C3B800407C010000A0 |
S2140031E04C218000000178009B0F0002040F800035 |
S2140031F09B0F00057C01C3FF4C21D27800200800FD |
S214003200C0220000A8000070D2B800086718001A94 |
S214003210C3AF003C65EF00154B0FC000C3AF0034D2 |
S21400322065EF00104B0FC000C3AF004045EFFFFF37 |
S2140032304B0FC000D7B80044A800005F0418000277 |
S2140032408AD800057C01C3FF4C21D260002008000C |
S214003250C0220000A800005C041800029AD80005EE |
S2140032607C01C3FF4C21D26400200800C02200006D |
S214003270A8000055C3A4004C07A50040B3FFFD4DB1 |
S214003280844000057C01C3FF4C21D26C002008005E |
S214003290C0220000A800004CC3B800404718000336 |
S2140032A0830000057C01C3FF4C21D2740020080077 |
S2140032B0C0220000A8000044C3B80040C3AF00749A |
S2140032C005EF00040B0FC000D7B80040C3B800409D |
S2140032D027180004D7B80040C3B800407C0102009D |
S2140032E0000178009B0F00037C01FE0000017800BF |
S2140032F09B0F00057C01C3FF4C21D27800200800FC |
S214003300C0220000A8000030D2B800086718001AD3 |
S214003310C3AF00407C0103FF4C21FFFF41E1780072 |
S2140033204B0FC000D7B80044A800002304180002C2 |
S2140033308AD800057C01C3FF4C21D260002008001B |
S214003340C0220000A8000020041800029AD8000539 |
S2140033507C01C3FF4C21D26400200800C02200007C |
S214003360A8000019C3A4004C07A5003CB3FFFCEF5F |
S214003370844000057C01C3FF4C21D2680020080071 |
S214003380C0220000A8000010D2B800086718001A73 |
S214003390C3AF003C65EF00154B0FC000D7B8004424 |
S2140033A0A80000057C01C3FF4C21D25C0020080069 |
S2140033B0C0220000A8000004C3B80078C3AF0044D1 |
S2140033C0D70F000000001000C3B40010C3B50014EF |
S2140033D0C3B60018C3B7001CC3BF002007BD0070EB |
S2140033E0AFE000000FBD0020D7BF0010D7A400201C |
S2140033F0D7A50024C3B80024870000097C01C3FFBA |
S2140034004C21DC14000120007C01C3FF4C21D47049 |
S21400341000012800C3A60020B0000CF2A800000996 |
S2140034207C01C3FF4C21DC14000120007C01C3FF9B |
S2140034304C21D46600012800C3A60020C3A70024A0 |
S214003440B0000CE8C3BF001007BD0020AFE00000CE |
S2140034500FBD0020D7BF0014D7A40020D7A5002496 |
S214003460D7A60028C3B80028DBB800287C01C3FF15 |
S2140034704C21DC14000120007C01C3FF4C21D458F1 |
S21400348000012800C3A60020C3A70024CBB800284C |
S214003490D7B80010B0000CD3C3BF001407BD00207F |
S2140034A0AFE000000FBD0020D7BF0014D7A4002057 |
S2140034B0D7A50024D7A60028C3B80028DBB8002864 |
S2140034C07C01C3FF4C21DC14000120007C01C3FFFB |
S2140034D04C21D44A00012800C3A60020C3A700241C |
S2140034E0CBB8002867180010D7B80010B0000CBD85 |
S2140034F0C3BF001407BD0020AFE000000FBD0020D2 |
S214003500D7BF0018D7A40020D7A50024D7A6002828 |
S214003510D7A7002CC3B8002CDBB8002C7C01C3FF57 |
S2140035204C21DC14000120007C01C3FF4C21D43860 |
S21400353000012800C3A60020C3A70024C3B80028A3 |
S214003540D7B80010CBB8002CD7B80014B0000CA524 |
S214003550C3BF001807BD0020AFE000000FBD00404D |
S214003560D7B3001CD7B40020D7B50024D7B60028A0 |
S214003570D7B7002CD7BF0030D7A40040D7A500444B |
S214003580D7A600480007B8007C01C3FF4C21DC1416 |
S214003590000120007C01C3FF4C21D4240001280038 |
S2140035A0C3A60040C3A70044C3B80048D7B800105D |
S2140035B046F8FFFF47188000830000047C01C3FF25 |
S2140035C04C21D4220001B000A80000037C01C3FFF8 |
S2140035D04C21D4200001B000D7B6001446F8FFFFF7 |
S2140035E0471880008300000D46F8FFFF471880004C |
S2140035F08300000446F8FFFF7C01FFFF4B01A0009C |
S214003600A800000246F8FFFF4714FFFF0014C000A2 |
S2140036100818C0000018A800A800000A46F8FFFF17 |
S214003620471880008300000446F8FFFF7C01FFFF78 |
S2140036304B019800A800000246F8FFFF4713FFFF63 |
S2140036400013A800D7B50018B0000C66C3B3001C62 |
S214003650C3B40020C3B50024C3B60028C3B7002CEB |
S214003660C3BF003007BD0040AFE000000FBD002024 |
S214003670D7BF0018D7A40020D7A50024D7A60028B7 |
S214003680D7A7002C7C01C3FF4C21DC1400012000CE |
S2140036907C01C3FF4C21D40F00012800C3A60020E4 |
S2140036A0C3A70024C3B80028D7B80010C3B8002C9E |
S2140036B0D7B80014B0000C4BC3BF001807BD0020DD |
S2140036C0AFE000000FBD0030D7B60018D7B7001C1B |
S2140036D0D7BF0020D7A40030D7A50034D7A600381F |
S2140036E00007B8007C01C3FF4C21DC140001200059 |
S2140036F07C01C3FF4C21D3FD00012800C3A6003087 |
S214003700C3A70034C3B80038D7B8001046F8FFFF88 |
S214003710471880008300000446F8FFFF7C01FFFF87 |
S2140037204B01B000A800000246F8FFFF4716FFFF57 |
S214003730C3B800400718000466CF0002030FC0009D |
S214003740D7B80014B0000C27C3B60018C3B7001CC7 |
S214003750C3BF002007BD0030AFE000000FBD002053 |
S214003760D7B60010D7B70014D7BF0018D7A40020CC |
S2140037700005B800D7A600287C01C3FF4C21DC1446 |
S214003780000120007C01C3FF4C21D4660001280004 |
S214003790C3A600207C01020042E1C00083000003B3 |
S2140037A07C01FC004AE1B000A80000037C0103FF96 |
S2140037B04C21FFFF42E1B000C3B800280718000400 |
S2140037C066CF0002030F3800B0000C06C3B6001028 |
S2140037D0C3B70014C3BF001807BD0020AFE0000049 |
S2140037E00FBD0020D7BF0010D7A40020D7A5002407 |
S2140037F07C01C3FF4C21DC14000120007C01C3FFC8 |
S2140038004C21D3F400012800C3A60020C3A700243F |
S214003810B0000BF4C3BF001007BD0020AFE00000EF |
S2140038200FBD0030D7B60014D7B70018D7BF001C9E |
S214003830D7A40030D7A50034C3B800306F18001ADC |
S2140038404718003FDFB8002FD3B8002F67180002D4 |
S2140038507C01C3FF4C21DB0C00380800C037000099 |
S2140038600017C000870000067C01C3FF4C21D3F080 |
S2140038700001200000002800B3FFFEDAA80000A127 |
S214003880C2F6000492C0009B0418000AA2D8009951 |
S21400389066D800027C01C3FF4C21D3A00038080084 |
S2140038A0C0380000AF000000C2E40000C3B800301B |
S2140038B07C0103FF4C21FFFF43012800B3FFFEC934 |
S2140038C0A8000090C2E40000C3B800306F0F0010DC |
S2140038D045EF001F000F28004718FFFF4706FFFFB1 |
S2140038E0B3FFFEDBA8000087C2E40000C3B80030C8 |
S2140038F06F0F001045EF001F000F28004718FFFF4E |
S2140039004706FFFFB3FFFEE7A800007EC2E4000004 |
S214003910C3B800306F0F001045EF001F000F2800DF |
S2140039206F0F001545EF001F000F30004718FFFF10 |
S2140039304707FFFFB3FFFEF1A8000072C2E40000D5 |
S214003940C3B800306F0F001045EF001F000F2800AF |
S2140039506F0F001545EF001F000F30004718FFFFE0 |
S2140039604707FFFFB3FFFEFDA8000066C2E40000A5 |
S214003970C3B800306F0F000B45EF001F000F280084 |
S2140039806F0F001545EF001F000F30006F18001076 |
S2140039904718001F00183800B3FFFF34A80000596E |
S2140039A0D3B8002F471800018700000DC2E40000BE |
S2140039B0C3B800306F0F000B45EF001F000F280044 |
S2140039C06F0F001545EF001F000F30006F18001036 |
S2140039D04718001F00183800B3FFFF24A80000494E |
S2140039E0C2E40000C3B800306F0F001045EF001FA0 |
S2140039F0000F28006F0F001545EF001F000F300066 |
S214003A004718FFFF4707FFFFB3FFFEBCA800003DB7 |
S214003A10D3B8002F471800018700000DC2E400004D |
S214003A20C3B800306F0F000B45EF001F000F2800D3 |
S214003A306F0F001545EF001F000F30006F180010C5 |
S214003A404718001F00183800B3FFFF08A800002D15 |
S214003A50C2E40000C3B800306F0F001045EF001F2F |
S214003A60000F28006F0F001545EF001F000F3000F5 |
S214003A704718FFFF4707FFFFB3FFFEB8A800002167 |
S214003A80C2E40000C3B800306F0F001545EF001FFA |
S214003A90000F28006F0F001045EF001F000F3000CA |
S214003AA04718FFFF4707FFFFC3B80034D7B800101A |
S214003AB0B3FFFF04A8000013C2E40000C3B8003040 |
S214003AC07C0103FF4C21FFFF43012800C3A60034FE |
S214003AD0B3FFFF22A800000BC2E40000C3B800300A |
S214003AE06F1800154718001F00182800B3FFFF3C8A |
S214003AF0A80000047C01C3FF4C21D3CC00012000A9 |
S214003B00B0000B0F7C01C3FF4C21DC140001100039 |
S214003B10C3B60014C3B70018C3BF001C07BD0030EF |
S214003B20AFE000000FBD0010D7B60000D7B7000406 |
S214003B307C01C3FF4C21DC7C00240800D038000048 |
S214003B400018B8000418003096F80004041800396D |
S214003B50A6F800020EF70030A800000E0418004178 |
S214003B6096F8000404180046A6F800020EF7003780 |
S214003B70A80000080418006196F8000404180066FF |
S214003B80A6F800020EF70057A80000020402FFFF86 |
S214003B90A800001B7C01C3FF4C21DC7D002408002C |
S214003BA0D03800000018B0000418003096D8000482 |
S214003BB004180039A6D800020ED60030A800000E61 |
S214003BC00418004196D8000404180046A6D800023F |
S214003BD00ED60037A80000080418006196D8000426 |
S214003BE004180066A6D800020ED60057A8000002E9 |
S214003BF00402FFFFA800000266F800044B1610003F |
S214003C00C3B60000C3B7000407BD0010AFE0000055 |
S214003C100FBD0020D7BF0010D7A40020D7A50024D2 |
S214003C20C3B8002087000004C3B800240018200092 |
S214003C30B0000CA5A8000003C3B80024001820009C |
S214003C40B0000CBCC3BF001007BD0020AFE00000F2 |
S214003C500FBD0020D7BF0010D7A40020C3B8002097 |
S214003C6087000003B0000C870002C000A800000216 |
S214003C70B0000C9C0002C000C3BF001007BD0020AF |
S214003C80AFE000000FBD0020D7BF0010D7A4002073 |
S214003C90C3B8002087000003B0000C7F0002C000FD |
S214003CA0A8000002B0000C950002C000C3BF0010C0 |
S214003CB007BD0020AFE000000FBD0070D7B00010B9 |
S214003CC0D7B10014D7B20018D7B3001CD7B4002061 |
S214003CD0D7B50024D7B60028D7B7002CD7BF0030FA |
S214003CE00004B8007C01C3FF4C21D5E00001200091 |
S214003CF0B0000A930000A800001720000405007317 |
S214003D00B3FFFFC30000B00000172000B3FFFFD0D2 |
S214003D1080400001A800000506D600017C010005D1 |
S214003D204C2157300001C00092D8FFF77C010005F7 |
S214003D304C2157300001C0009AD80001A8000007A7 |
S214003D407C01C3FF4C21D5CA00012000B0000A7CCC |
S214003D5006B500010418000A92B8FFE70418000A26 |
S214003D6082B8000400172000B3FFFFC6040F0061EE |
S214003D70804F00057C01C3FF4C21D59A000120002E |
S214003D80B0000A6FA800011A0017200004050061A1 |
S214003D90B3FFFF9F7C01C3FF4C21D57F00012000AD |
S214003DA0B0000A6704180001D7B8006CA800010725 |
S214003DB00017200004050072B3FFFF950000A8005E |
S214003DC000172000B3FFFFAF0002C0007C01C3FF56 |
S214003DD04C21DC7C00350800DC3800007C01C3FF89 |
S214003DE04C21DC7C00350800D0380000040F000AA7 |
S214003DF0870F0001A800000306B50001041802089A |
S214003E0092B8FFEF0418020886B800057C01C3FFCD |
S214003E104C21D55600012000B0000A49A80000ED4C |
S214003E207C01C3FF4C21DC7C00350800DC20000050 |
S214003E307C01C3FF4C21D552000120007C01C3FF4A |
S214003E404C21DC7C00012800B0000A3D7C01C3FF49 |
S214003E504C21DC7C00200800D0380000040F005302 |
S214003E60830F00057C01C3FF4C21D53600012000DE |
S214003E70B0000A33A80000D77C01C3FF4C21DC7DCC |
S214003E8000200800D030000004040002B3FFFF2525 |
S214003E9000029000665800010718000482B800056A |
S214003EA07C01C3FF4C21D50900012000B0000A2484 |
S214003EB0A80000C80000A00004160002A800000425 |
S214003EC000162000B3FFFF170282A00006D60002ED |
S214003ED092D5FFFB041800FF468F00FF81F800050F |
S214003EE07C01C3FF4C21D4E500012000B0000A1479 |
S214003EF0A80000B804180030921800AF0418003963 |
S214003F00A21800AD661800027C01C3FF4C21D3B88E |
S214003F1000380800C0380000AF00000004040004A9 |
S214003F20B3FFFF000002C000D7B800680404000614 |
S214003F30B3FFFEFCC3AF006865EF000849E28800E7 |
S214003F407C01C0004A2188000000B000A8000009DB |
S214003F5066D8000107040008B3FFFEF200029800CE |
S214003F600016C00002382000466500FFB00003D3EC |
S214003F7006D600010E58000392D8FFF5A80000935D |
S214003F8004040004B3FFFEE70002C000D7B80064D4 |
S214003F9004040006B3FFFEE30002C000D7B80060CA |
S214003FA0040F0008000F2000B3FFFEDEC3AF00645E |
S214003FB065EF0010C3AE006065CE000849EE7800DD |
S214003FC049E288007C01C0004A2188000000B00059 |
S214003FD0A800000966D800010704000AB3FFFED156 |
S214003FE0000298000016C00002382000466500FF58 |
S214003FF0B00003B206D600010E58000492D8FFF5B2 |
S214004000A800007204040004B3FFFEC60002C0004D |
S214004010D7B8005C04040006B3FFFEC20002C0006E |
S214004020D7B8005804040008B3FFFEBE0002C00064 |
S214004030D7B800540404000AB3FFFEBAC3AF005C4E |
S21400404065EF0018C3AE005865CE001A49EE78003A |
S214004050C3AE005465CE000849EE780049E28800F9 |
S2140040607C01C0004A2188000000B000A8000009BA |
S21400407066D800010704000CB3FFFEAA00029800F1 |
S2140040800016C00002382000466500FFB000038B13 |
S21400409006D600010E58000592D8FFF5A800004B82 |
S2140040A004040004B3FFFE9F0002C000D7B800500F |
S2140040B004040006B3FFFE9B0002C000D7B8004C05 |
S2140040C004040008B3FFFE970002C000D7B80048FB |
S2140040D00404000AB3FFFE930002C000C3AF005002 |
S2140040E065EF0018C3AE004C65CE001A49EE7800A6 |
S2140040F0C3AE004865CE000849EE780049F888004F |
S2140041007C01C0004A21880000112000B000009603 |
S214004110D7A0006CA800002D04040004B3FFFE81A5 |
S2140041200002C000D7B8004404040006B3FFFE7DBA |
S2140041300002C000D7B80040040F0008000F20009F |
S214004140B3FFFE780002C000C3AF004465EF001066 |
S214004150C3AE004065CE000849EE780049F88800F6 |
S2140041607C01C0004A21880000112000B000007EBB |
S214004170D7A0006CA800001504040004B3FFFE6975 |
S2140041800002C000D7B8003C04040006B3FFFE657A |
S2140041900002C000C3AF003C65EF000849F8880085 |
S2140041A07C01C0004A21880000112000B000006E8B |
S2140041B0D7A0006CA80000057C01C3FF4C21D4C327 |
S2140041C000012000B000095ED7A0006CC3B8006CE8 |
S2140041D08700FEF70017200004050071B3FFFE8C71 |
S2140041E07C01C3FF4C21D4A000012000B00009547C |
S2140041F0C3B00010C3B10014C3B20018C3B3001C90 |
S214004200C3B40020C3B50024C3B60028C3B7002C2F |
S214004210C3BF003007BD0070AFE000000FBD003028 |
S214004220D7B60014D7B70018D7BF001C0004B800D4 |
S21400423000172000B3FFEF7D0002B00086C0000527 |
S2140042407C01C3FF4C21D65900012000B000093C78 |
S214004250A800003B7C01C3FF4C21D62D00012000A6 |
S21400426000162800B000093600172000040500726A |
S214004270000030000000380004180001D7B8001015 |
S214004280B3FFEF6B804000057C01C3FF4C21D620B6 |
S21400429000012000B000092AA80000297C01C00007 |
S2140042A04C2101FE00012000B00002FB0002C0000D |
S2140042B0DFB8002F7C01C0004C2101FF0001200068 |
S2140042C0B00002F50002C000DFB8002ED3B8002F01 |
S2140042D0040F0055870F0003D3B8002E040F00AA62 |
S2140042E0830F00057C01C3FF4C21D6080001200087 |
S2140042F0B0000913A80000120404001000172800DC |
S214004300B00000250404001100002800B0000022C0 |
S2140043100404001200162800B000001F0404001D4C |
S2140043207C01C0004C21100000012800B000001ADB |
S2140043307C01C00000012000B000000BB00001DAD4 |
S214004340C3B60014C3B70018C3BF001C07BD0030B7 |
S214004350AFE000007C01C3FF4C21DF1800200800FE |
S214004360C0220000AFE000007C01C3FF4C21DF1834 |
S21400437000200800D4240000AFE000004498001F8E |
S214004380671800027C01C3FF4C21DE940038080049 |
S214004390C0220000AFE000004498001F8300000722 |
S2140043A04498001F671800027C01C3FF4C21DE946E |
S2140043B000380800D4250000A8000000AFE0000088 |
S2140043C07C01C3FF4C21DF1400200800C02200003F |
S2140043D0AFE000007C01C3FF4C21DF140020080082 |
S2140043E0D4240000AFE000007C01C3FF4C21DE9027 |
S2140043F000200800C0220000AFE000007C01C3FFE0 |
S2140044004C21DE8C00200800C0220000AFE0000037 |
S2140044107C01C3FF4C21DE8C00200800D424000061 |
S214004420041800017C01C3FF4C21DE900020080028 |
S214004430D4380000AFE000007C01C3FF4C21DE90C2 |
S21400444000200800D4200000AFE0000090800003A9 |
S2140044500004C000040F0020970F00047C01C3FF77 |
S2140044604C21D7D100011000A80000056498000276 |
S2140044707C01C3FF4C21D66C00380800C022000027 |
S214004480AFE000000FBD0020D7BF0010D7A400206B |
S214004490D7A50024D7A60028C3B800209300003A6A |
S2140044A0040F0009A30F0038671800027C01C3FF41 |
S2140044B04C21D72C00380800C0380000AF000000A0 |
S2140044C0C3B80024C3AF0028870F003404020001DD |
S2140044D0A8000033C3B80024C3AF0028830F002F02 |
S2140044E004020001A800002EC3B80024C3AF0028B1 |
S2140044F0A30F002A04020001A8000029C3B8002464 |
S214004500C3AF0028A70F002504020001A80000245E |
S214004510C3B80024C3AF00289B0F0020040200018C |
S214004520A800001FC3B80024C3AF00289F0F001BBD |
S21400453004020001A800001AC3B80024C3AF002874 |
S214004540930F001604020001A8000015C3B800244B |
S214004550C3AF0028970F001104020001A800001046 |
S214004560C3B80024C3AF00288B0F000C0402000160 |
S214004570A800000BC3B80024C3AF00288F0F0007A5 |
S21400458004020001A80000067C01C3FF4C21D7AF3F |
S21400459000012000C3A50020B0000869000010003C |
S2140045A0C3BF001007BD0020AFE000000FBD0070C5 |
S2140045B0D7B30010D7B40014D7B50018D7B6001C70 |
S2140045C0D7B70020D7BF00247C01C3FF4C21DF18DB |
S2140045D000200800C0240000B00002290002B0003D |
S2140045E06ED8001A4718003FD7B8006C6ED8001572 |
S2140045F04718001FD7B800306ED800104718001FA5 |
S214004600D7B8002846D8FFFFDBB8002E7C0103FF92 |
S2140046104C21FFFF42C1C000D7B800340418000187 |
S214004620D7B80068C3B8006C7C01C3FF4C21D6EC39 |
S21400463000380800D0340000041800019298004AA0 |
S21400464004180004A2980048669800027C01C3FF84 |
S2140046504C21D75000380800C0380000AF000000DA |
S2140046607C01C3FF4C21DF1800200800C038000082 |
S21400467007150004A80000427C01C3FF4C21DF1888 |
S21400468000200800C038000007150004C3B8006CFE |
S2140046900F040020C3B80030671800027C01C3FF77 |
S2140046A04C21DE9400380800C0250000C3B800285E |
S2140046B0671800027C01C3FF4C21DE940038080016 |
S2140046C0C0260000B3FFFF6F8040002DCBB8002E41 |
S2140046D04718800083000004CBB8002E7C01FFFF43 |
S2140046E04B019800A8000002CBB8002E4713FFFF2E |
S2140046F06678000202B8A800A8000021C3B80034FB |
S2140047007C0102004301C00083000004C3B80034EB |
S2140047107C01FC004B019800A8000004C3B80034DC |
S2140047207C0103FF4C21FFFF430198007C01C3FF7F |
S2140047304C21DF1800200800C038000007180004CD |
S214004740666F0002030FA800A800000DC3B8003073 |
S214004750671800027C01C3FF4C21DE940038080075 |
S214004760C0350000A80000067C01C3FF4C21D77CA2 |
S21400477000012000C3A5006CB00007F1D7A00068B8 |
S214004780C3B800688700000200001000A80000BE42 |
S21400479000152000B00001BAD7A200640015200062 |
S2140047A00418002E6718001A00182800B00001BD73 |
S2140047B00000B80066F800027C01C3FF4C21DE94BE |
S2140047C000380800C02F00007C01C3FF4C21DA74BB |
S2140047D000380800D42F000006F700010418002057 |
S2140047E092F8FFF47C01C3FF4C21DF18002008007C |
S2140047F0C03800007C01C3FF4C21DAEC0020080022 |
S214004800D43800007C01C3FF4C21DF1400200800D0 |
S214004810C03800007C01F7FF4C21FFFF4301C000B9 |
S2140048207C01C3FF4C21DAF400200800D4380000D5 |
S214004830B00001A57C01C3FF4C21DAF80020080077 |
S214004840D4220000B00001AA7C01C3FF4C21DAFC90 |
S21400485000200800D4220000B00001AF7C01C3FF96 |
S2140048604C21DB0000200800D422000007A4003CF6 |
S214004870B3FFEE388040000B7C01C3FF4C21DA709A |
S21400488000200800C0380000D7B8003807B8003C41 |
S2140048907C01C3FF4C21DA7000200800D4380000E9 |
S2140048A0B3FFEE49C3B800387C01C3FF4C21DA7071 |
S2140048B000200800D43800000000B80082E0000A9B |
S2140048C066F800027C01C3FF4C21DA740038080049 |
S2140048D0C02F00007C01C3FF4C21DE940038080086 |
S2140048E0D42F0000A800000006F7000104180020DE |
S2140048F092F8FFF27C01C3FF4C21DAEC002008009E |
S214004900C03800007C01C3FF4C21DF1800200800DF |
S214004910D43800007C01C3FF4C21DAF400200800E4 |
S214004920C03800007C01C3FF4C21DF1400200800C3 |
S214004930C02F00007C01080041E178004B0FC0004A |
S2140049407C01C3FF4C21DF1400200800D43800008F |
S2140049507C01C3FF4C21DAF800200800C0240000C8 |
S214004960B000015E7C01C3FF4C21DAFC0020080089 |
S214004970C0240000B00001637C01C3FF4C21DB00B3 |
S21400498000200800C0240000B000016800152000C8 |
S214004990C3A50064B00001437C01C3FF4C21DF18AF |
S2140049A000200800C038000086B80002040200019B |
S2140049B0A80000357C01C3FF4C21DF14002008004E |
S2140049C0C03800007C0108004301C00087000011C9 |
S2140049D07C01C3FF4C21DF1400200800C038000013 |
S2140049E07C01001F4301C0006F1800100018200053 |
S2140049F0B3FFFE960002C0007C01C3FF4C21D764C3 |
S214004A000001200000182800B000074D000010002C |
S214004A10A800001D7C01C3FF4C21DF140020080005 |
S214004A20C03800007C01001F4301C0006F18001052 |
S214004A30040F0015870F000CB000012D7C018000CC |
S214004A404041C000870000087C01C0004C210008DF |
S214004A500001C0007C01C3FF4C21DF1800200800C5 |
S214004A60D4380000A80000077C01C0004C210004D8 |
S214004A700001C0007C01C3FF4C21DF1800200800A5 |
S214004A80D438000004020001C3B30010C3B40014FD |
S214004A90C3B50018C3B6001CC3B70020C3BF0024AC |
S214004AA007BD0070AFE000000FBD0050D7B5001086 |
S214004AB0D7B60014D7B70018D7BF001C7C01C3FFB9 |
S214004AC04C21DE9000200800C0380000830000E47F |
S214004AD07C01C3FF4C21DE8C00200800C03800009B |
S214004AE07C01C3FF4C21DF1800200800C02F000007 |
S214004AF0870F00DBB3FFFEAD844000D90000100036 |
S214004B00A80000D97C01C3FF4C21DE9000200800DD |
S214004B10C03800008300000E7C01C3FF4C21DE8CF1 |
S214004B2000200800C0240000B00000D50002A80045 |
S214004B307C01C3FF4C21DE8C00200800C02400004E |
S214004B400418002E6718001A00182800B00000D5B8 |
S214004B500000B80066F800027C01C3FF4C21DE941A |
S214004B6000380800C02F00007C01C3FF4C21DA7417 |
S214004B7000380800D42F000006F7000104180020B3 |
S214004B8092F8FFF47C01C3FF4C21DF1800200800D8 |
S214004B90C03800007C01C3FF4C21DAEC002008007E |
S214004BA0D43800007C01C3FF4C21DF14002008002D |
S214004BB0C03800007C01F7FF4C21FFFF4301C00016 |
S214004BC07C01C3FF4C21DAF400200800D438000032 |
S214004BD0B00000BD7C01C3FF4C21DAF800200800BD |
S214004BE0D4220000B00000C27C01C3FF4C21DAFCD6 |
S214004BF000200800D4220000B00000C77C01C3FFDC |
S214004C004C21DB0000200800D422000007A4002866 |
S214004C10B3FFED508040000A7C01C3FF4C21DA70E0 |
S214004C2000200800C036000007B800287C01C3FF3B |
S214004C304C21DA7000200800D4380000B3FFED6283 |
S214004C407C01C3FF4C21DA7000200800D436000037 |
S214004C500000B80082E0000A66F800027C01C3FF8C |
S214004C604C21DA7400380800C02F00007C01C3FF16 |
S214004C704C21DE9400380800D42F0000A800000065 |
S214004C8006F700010418002092F8FFF27C01C3FF2B |
S214004C904C21DAEC00200800C03800007C01C3FF7D |
S214004CA04C21DF1800200800D43800007C01C3FF28 |
S214004CB04C21DAF400200800C03800007C01C3FF55 |
S214004CC04C21DF1400200800C02F00007C010800E3 |
S214004CD041E178004B0FC0007C01C3FF4C21DF147C |
S214004CE000200800D43800007C01C3FF4C21DAF80D |
S214004CF000200800C0240000B00000787C01C3FF3C |
S214004D004C21DAFC00200800C0240000B000007D22 |
S214004D107C01C3FF4C21DB0000200800C0240000FB |
S214004D20B00000827C01C3FF4C21DE90002008000A |
S214004D30C0380000830000067C01C3FF4C21DE8CD7 |
S214004D4000200800C024000000152800B000005510 |
S214004D507C01C3FF4C21DE9000200800C038000014 |
S214004D608300000B7C01C3FF4C21DE8C0020080072 |
S214004D70C03800007C01C3FF4C21DF18002008006B |
S214004D80C02F0000870F000204020001A8000036B2 |
S214004D907C01C3FF4C21DF1400200800C03800004F |
S214004DA07C0108004301C000870000117C01C3FF9E |
S214004DB04C21DF1400200800C03800007C01001FD2 |
S214004DC04301C0006F18001000182000B3FFFD9FBD |
S214004DD00002C0007C01C3FF4C21D7640001200004 |
S214004DE000182800B000065600001000A800001E9C |
S214004DF07C01C3FF4C21DF1400200800C0380000EF |
S214004E007C01001F4301C0006F180010040F00153E |
S214004E10870F000CB00000367C0180004041C000C7 |
S214004E20870000087C01C0004C2100080001C0007B |
S214004E307C01C3FF4C21DF1800200800D438000096 |
S214004E40A80000077C01C0004C2100040001C0003F |
S214004E507C01C3FF4C21DF1800200800D438000076 |
S214004E60ABFFFF2800001000C3B50010C3B6001447 |
S214004E70C3B70018C3BF001C07BD0050AFE000005A |
S214004E800004C000C3020000AFE000000004C00041 |
S214004E90CB020000AFE000000004C000D302000018 |
S214004EA0AFE000000004C000D7050000AFE000003F |
S214004EB00004C000DB050000AFE000000004C000F6 |
S214004EC0DF050000AFE000007C01C3FF4C21DF28B7 |
S214004ED000200800C0220000AFE000007C01C3FFF5 |
S214004EE04C21DF2800200800D4240000AFE000009A |
S214004EF07C01C3FF4C21DF2400200800C0220000F4 |
S214004F00AFE000007C01C3FF4C21DF240020080036 |
S214004F10D4240000AFE000007C01C3FF4C21DF205A |
S214004F2000200800C0220000AFE000007C01C3FFA4 |
S214004F304C21DF2000200800D4240000AFE0000051 |
S214004F400FBD0040D7B50010D7B60014D7B700186D |
S214004F50D7BF001CD7A40040D7A50044C3A4004474 |
S214004F60B3FFEC61D7A2002CC3A40044B3FFEC62ED |
S214004F700002B800C3B8002C7C01FFFF4C21F000F3 |
S214004F804301C000D7B800307C01FFFF4C21F00081 |
S214004F9042E1C000D7B8003446F8000283000002A1 |
S214004FA004160001A80000010000B000D7B60038C3 |
S214004FB046F800018300000204150001A800000165 |
S214004FC00000A800D7B5003CC3B8004007A80030D2 |
S214004FD0C1030000C1090004D7030000D70900047C |
S214004FE0C1030008C109000CD7030008D709000C4C |
S214004FF0C3B50010C3B60014C3B70018C3BF001C67 |
S21400500007BD0040AFE000000FBD0020D7B700107E |
S214005010D7BF0014D7A40020D7A50024D7A6002801 |
S214005020D7A7002C0000B800C3B8002C83000001EE |
S2140050304EF70002C3B80030830000014EF70001AF |
S214005040C3A40020C3A50024C3B800284B17300013 |
S214005050B3FFEC2DC3B70010C3BF001407BD00207C |
S214005060AFE000000FBD0030D7B20010D7B3001479 |
S214005070D7B40018D7B5001CD7B60020D7B7002481 |
S214005080D7BF00280004B80000172000B00005AC09 |
S214005090000098007C01C3FF4C21DF800020080040 |
S2140050A0C0340000A80000BEB00002C20002A80083 |
S2140050B066B20018765200180418000D8258000BCD |
S2140050C00418000E8258006F041800108258001B47 |
S2140050D0A2580003041800088258000EA800009B7F |
S2140050E00418007F8258000BA80000980404000AE9 |
S2140050F0B00002B97C01C3FF4C21DF30003308004A |
S214005100DC2000007C01C3FF4C21DF3000011000D2 |
S214005110A80000A586600001A80000A104040008FD |
S214005120B00002AD04040020B00002AB0404000886 |
S214005130B00002A90E730001A80000997C01C3FF0D |
S2140051404C21DF8000200800C0380000869800113F |
S2140051507C01C3FF4C21DF3000330800DC20000058 |
S214005160041800507C01C3FF4C21DF80002008009B |
S214005170C02F0000130FC0007C01C3FF4C21DF844A |
S214005180030120007C01C3FF4C21DF300001280012 |
S214005190B00000E30E9600010418FFFF86D8000159 |
S2140051A0041600137C01C3FF4C21DF80002008009A |
S2140051B0C038000086D8000304040007B00002864A |
S2140051C0A8000077041800501316C0007C01C3FF27 |
S2140051D04C21DF8400380800CC380000870000032C |
S2140051E004040007B000027CA800006D0016A000B2 |
S2140051F07C01C3FF4C21DF30000120000418005062 |
S2140052001314C0007C01C3FF4C21DF840301280077 |
S214005210B00000C37C01C3FF4C21D9CA00012000A6 |
S214005220B00005470000B0007C01C3FF4C21D9C880 |
S21400523000012000B000054206D600010418004F09 |
S21400524092D8FFF97C01C3FF4C21D9CA0001200087 |
S214005250B000053B00172000B00005397C01C3FFF5 |
S2140052604C21DF3000012000B00005357C01C3FF73 |
S2140052704C21DF3000012000B000008D00029800B5 |
S214005280A80000477C01C3FF4C21DF8000200800F7 |
S214005290C03800008698000304040007B000024EE1 |
S2140052A0A800003F069600010418001486D80001E6 |
S2140052B00000B0000016A0007C01C3FF4C21DF30C8 |
S2140052C000012000041800501314C0007C01C3FF26 |
S2140052D04C21DF8403012800B00000917C01C3FF4D |
S2140052E04C21D9CA00012000B00005150000B0000E |
S2140052F07C01C3FF4C21D9C800012000B000051076 |
S21400530006D600010418004F92D8FFF97C01C3FFAF |
S2140053104C21D9CA00012000B00005090017200062 |
S214005320B00005077C01C3FF4C21DF3000012000E0 |
S214005330B00005037C01C3FF4C21DF3000012000D4 |
S214005340B000005B00029800A800001566B80018C0 |
S21400535077180018040F0009870F000104150020B5 |
S21400536066B8001877180018040F0020930F000284 |
S214005370040F007E8B0F0001A800000966A4001829 |
S21400538074840018B00002140013C0000713000154 |
S2140053907C01C3FF4C21DF3000380800DC350000FC |
S2140053A0ABFFFF4100001000C3B20010C3B30014EF |
S2140053B0C3B40018C3B5001CC3B60020C3B700248E |
S2140053C0C3BF002807BD0030AFE000000FBD0020BF |
S2140053D0D7B60010D7B70014D7BF00180004B8001F |
S2140053E0CEF8000087000001A800002B7C01C3FF58 |
S2140053F04C21DF8000200800C03800000F16000196 |
S2140054000418FFFF86D80001041600130418005085 |
S2140054101316C0007C01C3FF4C21DF84030120006B |
S21400542000172800B000003084400001A800001AD1 |
S214005430041800507C01C3FF4C21DF8000200800C8 |
S214005440C02F0000130FC0007C01C3FF4C21DF8477 |
S2140054500301200000172800B00000317C01C3FFC4 |
S2140054604C21DF8000200800C0380000071800012B |
S2140054707C01C3FF4C21DF8000200800D4380000E8 |
S214005480040F0014870F00047C01C3FF4C21DF804B |
S21400549000200800D4200000C3B60010C3B70014D4 |
S2140054A0C3BF001807BD0020AFE00000AFE000005B |
S2140054B00FBD0010D7B700000004B800A800000118 |
S2140054C006F70001CEF800008700FFFD0017C000B9 |
S2140054D0000478000B0FC00000181000C3B70000CF |
S2140054E007BD0010AFE00000A8000006CC98000042 |
S2140054F08700000200001000A800000804840001D5 |
S21400550004A50001CC980000CCAF0000830FFFF785 |
S214005510CC980000CCAF00000B0F1000AFE00000EE |
S2140055200FBD0010D7B700000004B800A8000002A6 |
S21400553006F7000104A50001CCB80000DEF8000064 |
S21400554067180018771800188700FFF90004100085 |
S214005550C3B7000007BD0010AFE000000FBD00108D |
S214005560D7B700000004B800A800000106F7000145 |
S214005570CEF800008700FFFDA800000206F7000135 |
S21400558004A50001CCB80000DEF80000671800187B |
S214005590771800188700FFF900041000C3B7000052 |
S2140055A007BD0010AFE00000A8000005CC98000082 |
S2140055B08700000200001000A80000060484000116 |
S2140055C0CC98000064AF001875EF0018870FFFF73F |
S2140055D000041000AFE000000FBD0020D7B7001099 |
S2140055E0D7BF0014D7A400200005B800C3B8002019 |
S2140055F083000006C3B800207C01C3FF4C21E5C829 |
S21400560000200800D4380000A80000137C01C3FF67 |
S2140056104C21E5C800200800C0380000071800012B |
S2140056207C01C3FF4C21E5C800200800D4380000E8 |
S214005630A80000097C01C3FF4C21E5C80020080033 |
S214005640C0380000071800017C01C3FF4C21E5C8E4 |
S21400565000200800D43800007C01C3FF4C21E5C8B8 |
S21400566000200800C0380000CF18000083000005A6 |
S2140056700017200000182800B3FFFFCB0002C00070 |
S2140056808700FFEC7C01C3FF4C21E5C80020080022 |
S214005690C0380000CF18000087000002000010008D |
S2140056A0A80000357C01C3FF4C21E5C80020080097 |
S2140056B0C0380000070F00017C01C3FF4C21E5C87D |
S2140056C000200800D42F0000D7B8001CA80000094E |
S2140056D07C01C3FF4C21E5C800200800C03800004C |
S2140056E0071800017C01C3FF4C21E5C80020080014 |
S2140056F0D43800007C01C3FF4C21E5C80020080018 |
S214005700C0380000CF1800008300000500172000F6 |
S21400571000182800B3FFFFA40002C0008300FFECBF |
S2140057207C01C3FF4C21E5C800200800C0380000FB |
S214005730CF180000830000067C01C3FF4C21E5C89B |
S21400574000200800C0380000DF000000A8000009A4 |
S2140057507C01C3FF4C21E5C800200800C0380000CB |
S2140057600718FFFF7C01C3FF4C21E5C80020080096 |
S214005770D4380000C3A2001CC3B70010C3BF001477 |
S21400578007BD0020AFE000000FBD0010D7B7000037 |
S2140057906497001876F700180418000992F8000EAF |
S2140057A00418000DA2F8000666F800027C01C3FF8C |
S2140057B04C21D9A800380800C0380000AF0000000F |
S2140057C00418002082F80001A80000030418000155 |
S2140057D0D7B8000CA8000001D7A0000CC3A2000C8C |
S2140057E0C3B7000007BD0010AFE000000FBD0010FB |
S2140057F0D7B700006498001877180018040F003018 |
S214005800930F0007040F0039A30F000564980018D3 |
S214005810771800180F180030D4D80000A800001A17 |
S2140058206498001877180018040F0041930F0008BA |
S214005830040F005AA30F0006649800187718001883 |
S2140058400F1800410718000AD4D80000A800000E60 |
S2140058506498001877180018040F0061930F00086A |
S214005860040F007AA30F0006649800187718001833 |
S2140058700F1800610718000AD4D80000A80000021C |
S21400588000001000A8000006C0D800009B0500021B |
S21400589004170001A80000010000B800001710005F |
S2140058A0C3B7000007BD0010AFE000000FBD00301A |
S2140058B0D7B50010D7B60014D7B70018D7BF001C4E |
S2140058C00004B800D7A500340006B0000000A80009 |
S2140058D0A800000106F70001CEE40000B3FFFFAA0F |
S2140058E08440FFFCCEF80000040F002B870F000456 |
S2140058F004180001D7B8002806F70001A800000920 |
S214005900CEF80000040F002D870F00040418FFFFD8 |
S214005910D7B8002806F70001A80000020418000106 |
S214005920D7B8002882C000020418001086D80019D4 |
S214005930CEF80000040F0030870F0008CEF80001F4 |
S214005940040F0078830F0002040F0058870F00032F |
S21400595006F7000204160010A800000E86C0000D10 |
S214005960CEF80000040F0030870F000306F7000192 |
S21400597004160008A80000070416000AA800000580 |
S2140059800016C0001AB8A800C3B8002C02B8A800B9 |
S21400599006F70001CEE400000016280007A6002C3B |
S2140059A0B3FFFF928440FFF6C3B8003483000002C2 |
S2140059B0C3B80034D7170000C3B800281B15100062 |
S2140059C0C3B50010C3B60014C3B70018C3BF001C8D |
S2140059D007BD0030AFE000000FBD0010D7B70000D5 |
S2140059E0A80000080004C000CF170000070400014C |
S2140059F0CCAF0000DF0F00000005C0000705000167 |
S214005A00DF1700000006C0000F0600018700FFF544 |
S214005A10C3B7000007BD0010AFE000000FBD0030A8 |
S214005A20D7B10010D7B20014D7B30018D7B4001CF3 |
S214005A30D7B50020D7B60024D7B70028D7BF002C8C |
S214005A400004B8000005B0000006A8000007A0008B |
S214005A5000179800001690000016C0000017780087 |
S214005A600B0FC0002315C000271800021315C00036 |
S214005A7003178800A800000102B398000013200056 |
S214005A80001128000014C800B72000009040FFFA5C |
S214005A90A80000010A5590000011200000122800FE |
S214005AA00014C800B72000009040FFFA0013C000A2 |
S214005AB000127800A70F000F0011C0000013780036 |
S214005AC0870F000200128800A80000040011C00022 |
S214005AD000127800870F00010013880000132000D2 |
S214005AE00012280000153000B3FFFFBB02B3980079 |
S214005AF00A5590000013C000001278008F0FFFDFD9 |
S214005B000017C000001278009F0F00050017200045 |
S214005B10001228000015300000143800B3FFFFBF45 |
S214005B200013C000001678009F0F00050013200029 |
S214005B30001628000015300000143800B3FFFFB729 |
S214005B40C3B10010C3B20014C3B30018C3B4001C22 |
S214005B50C3B50020C3B60024C3B70028C3BF002CBB |
S214005B6007BD0030AFE000000FBD0020D7BF00101B |
S214005B70D7A40020D7A50024D7A60028D7A7002C96 |
S214005B80C3B8002000182000C3AF0028C3AE00240E |
S214005B900DCE000111CF700001D82800000F300094 |
S214005BA0C3A7002CB3FFFF9DC3BF001007BD002096 |
S214005BB0AFE000000FBD0020D7BF0010B3FFE91410 |
S214005BC00002C0006702001874420018C3BF00102D |
S214005BD007BD0020AFE000000FBD0020D7BF0010BB |
S214005BE0D7A40020C3B80020DFB80020CFB800201C |
S214005BF0040F000A870F00020404000DB3FFE90635 |
S214005C00CFA40020B3FFE904C3BF001007BD0020E7 |
S214005C10AFE000000FBD0020D7B70010D7BF0014BC |
S214005C200004B800A8000003CEE40000B3FFFFEABB |
S214005C3006F70001CEF800008700FFFBC3B7001090 |
S214005C40C3BF001407BD0020AFE000000FBD00205A |
S214005C50D7B60010D7B70014D7BF00180004B80096 |
S214005C600000B0009AE0000206D600010817B8004F |
S214005C7026F8000AD7B8001CC3B8001C830000032F |
S214005C80C3A4001CB3FFFFF102C2B00006C20001AD |
S214005C90C3B60010C3B70014C3BF001807BD00206A |
S214005CA0AFE000000FBD0020D7B60010D7B7001435 |
S214005CB0D7BF0018D7A400200005B800D7A6002834 |
S214005CC00007B0009AC0000A001720000405002D47 |
S214005CD0C3B90020B72000000002B800C3B80028EF |
S214005CE0C30F000005EF0001D70F00000816B00034 |
S214005CF026D8000AD7B8001CC3B8001C83000006CC |
S214005D00C3A4002000172800C3A60028C3A7001CB1 |
S214005D10B3FFFFE40002B8000017200036D8000AE0 |
S214005D20071800306705001874A50018C3B90020CE |
S214005D30B72000000002B800C3B80028C30F000058 |
S214005D4005EF0001D70F000000171000C3B60010C3 |
S214005D50C3B70014C3BF001807BD0020AFE00000A3 |
S214005D600FBD0020D7BF0010D7A40020D7A5002461 |
S214005D70D7A00018C3B80020C3AF00242B0FC00064 |
S214005D80D7B8001CC3B8001C83000006C3A4001CC0 |
S214005D90C3A50024B3FFFFF2C3AF001801E2C000A2 |
S214005DA0D7B80018C3B8001807020001C3BF001018 |
S214005DB007BD0020AFE000000FBD0030D7B70018C9 |
S214005DC0D7BF001CD7A400300005B800D7A60038FF |
S214005DD0D7A7003CC3B8003CC3AF00402B0FC000A1 |
S214005DE0D7B8002CC3B8002C8300000AC3A4003028 |
S214005DF000172800C3A60038C3A7002CC3B800406D |
S214005E00D7B80010C3B80044D7B80014B3FFFFEAF1 |
S214005E100002B800C3B8004483000010001720003A |
S214005E20C3B8003CC3AF00403B0FC0007C01C3FFBB |
S214005E304C21D9F100380800CC250000C3B9003049 |
S214005E40B72000000002B800C3B80038C30F000037 |
S214005E5005EF0001D70F0000A800000F0017200074 |
S214005E60C3B8003CC3AF00403B0FC0007C01C3FF7B |
S214005E704C21D9E000380800CC250000C3B900301A |
S214005E80B72000000002B800C3B80038C30F0000F7 |
S214005E9005EF0001D70F000000171000C3B7001869 |
S214005EA0C3BF001C07BD0030AFE000000FBD0030D0 |
S214005EB0D7B30010D7B40014D7B50018D7B6001C57 |
S214005EC0D7B70020D7BF00240004B8000005B000F4 |
S214005ED00006A8000007A000C3B8004000189800FD |
S214005EE0A8000009001620006665001874A50018B2 |
S214005EF00017C800B72000000002B000C2B80000BB |
S214005F0007180001D6B800000014C0000F140001E6 |
S214005F10A300FFF400161000C3B30010C3B40014AF |
S214005F20C3B50018C3B6001CC3B70020C3BF002407 |
S214005F3007BD0030AFE000000FBD0070D7B00018FE |
S214005F40D7B1001CD7B20020D7B30024D7B400289E |
S214005F50D7B5002CD7B60030D7B70034D7BF003837 |
S214005F600004B8000005B0000006A8000007A00066 |
S214005F70D7A0006CA80001C966780018771800182A |
S214005F8087000002C3A2006CA80001C6001620000D |
S214005F906665001874A500180017C800B720000032 |
S214005FA00002B000C3B8006C07180001D7B8006C38 |
S214005FB00015C00007150001CF1800000018980053 |
S214005FC06718001877180018040F0025870FFFEAD7 |
S214005FD00015C00007150001CF13000066780018F2 |
S214005FE077180018040F002D870F0006041800010C |
S214005FF0001888000015C00007150001CF13000028 |
S214006000A8000001000088006678001877180018BD |
S214006010040F0030870F0005041000300015C00084 |
S21400602007150001CF130000A8000001041000208F |
S21400603000009000A80000090418000A131290003F |
S21400604066780018771800180F180030025890006D |
S2140060500015C00007150001CF1300006678001871 |
S21400606077180018040F0030930F0002040F003951 |
S2140060708B0FFFF16678001877180018040F00647D |
S214006080870F0026069800040018A000C318FFFC1F |
S214006090D7B80064C3A40064B3FFFEECD7A20068C0 |
S2140060A08A40000B8620000A0017200000162800F1 |
S2140060B007A6006CC3B800680A58380066180018AF |
S2140060C077180018D7B80010B3FFFF780002B000AA |
S2140060D0001720000016280007A6006CC3A700645F |
S2140060E0B3FFFEF00002B0008A40016C8220016B14 |
S2140060F0001720000016280007A6006CC3B800682A |
S2140061000A5838006618001877180018D7B8001014 |
S214006110B3FFFF660002B000A800016066780018B2 |
S21400612077180018040F0075830F0006040F006F21 |
S214006130830F0004040F0078830F0002040F00583A |
S214006140870F005C069800040018A000C318FFFC28 |
S214006150D7B80060C3A400606678001877180018E7 |
S214006160040F006F870F000304180008D7B800500C |
S214006170A800000D6678001877180018040F00783D |
S214006180830F0002040F0058870F00030418001046 |
S214006190D7B8004CA80000020418000AD7B8004C74 |
S2140061A0C3B8004CD7B80050C3B800500018280039 |
S2140061B0B3FFFEEBD7A200688A40000B8620000AD9 |
S2140061C0001720000016280007A6006CC3B8006859 |
S2140061D00A5838006618001877180018D7B8001044 |
S2140061E0B3FFFF320002B0000017200000162800A0 |
S2140061F007A6006CC3A7006066780018771800181A |
S214006200040F006F870F000304180008D7B8004873 |
S214006210A800000D6678001877180018040F00789C |
S214006220830F0002040F0058870F000304180010A5 |
S214006230D7B80044A80000020418000AD7B80044E3 |
S214006240C3B80044D7B80048C3B80048D7B8001051 |
S2140062506678001877180018040F0058870F000398 |
S21400626004180001D7B80040A8000001D7A00040DD |
S214006270C3B80040D7B80014B3FFFECF0002B0008A |
S2140062808A4001068220010500172000001628001B |
S21400629007A6006CC3B800680A58380066180018CD |
S2140062A077180018D7B80010B3FFFF000002B00040 |
S2140062B0A80000FA6678001877180018040F006C1B |
S2140062C0870F00A50015C00007150001CF130000BA |
S2140062D06678001877180018040F0064870F0026E9 |
S2140062E0069800040018A000C318FFFCD7B8005892 |
S2140062F0C3A40058B3FFFE55D7A200688A40000B1F |
S2140063008620000A001720000016280007A6006C4A |
S214006310C3B800680A5838006618001877180018BE |
S214006320D7B80010B3FFFEE10002B000001720004F |
S2140063300016280007A6006CC3A70058B3FFFE5936 |
S2140063400002B0008A4000D5822000D4001720004A |
S2140063500016280007A6006CC3B800680A58380064 |
S2140063606618001877180018D7B80010B3FFFECFCD |
S2140063700002B000A80000C9667800187718001858 |
S214006380040F0075830F0006040F006F830F0004D0 |
S214006390040F0078830F0002040F0058870F005C7C |
S2140063A0069800040018A000C318FFFCD7B80054D5 |
S2140063B0C3A400546678001877180018040F006FFE |
S2140063C0870F000304180008D7B80050A800000D77 |
S2140063D06678001877180018040F0078830F0002FC |
S2140063E0040F0058870F000304180010D7B8004C9D |
S2140063F0A80000020418000AD7B8004CC3B8004C26 |
S214006400D7B80050C3B8005000182800B3FFFE5499 |
S214006410D7A200688A40000B8620000A00172000DA |
S2140064200016280007A6006CC3B800680A58380093 |
S2140064306618001877180018D7B80010B3FFFE9B30 |
S2140064400002B000001720000016280007A6006C07 |
S214006450C3A700546678001877180018040F006F5A |
S214006460870F000304180008D7B80048A800000DDE |
S2140064706678001877180018040F0078830F00025B |
S214006480040F0058870F000304180010D7B8004404 |
S214006490A80000020418000AD7B80044C3B8004495 |
S2140064A0D7B80048C3B80048D7B8001066780018B8 |
S2140064B077180018040F0058870F0003041800010F |
S2140064C0D7B80040A8000001D7A00040C3B80040DD |
S2140064D0D7B80014B3FFFE380002B0008A40006F41 |
S2140064E08220006E001720000016280007A6006C09 |
S2140064F0C3B800680A5838006618001877180018DD |
S214006500D7B80010B3FFFE690002B000A800006311 |
S214006510001620000405006C0017C800B720000015 |
S2140065200002B000C3B8006C07180001D7B8006CB2 |
S214006530001620006665001874A500180017C8002D |
S214006540B72000000002B000C3B8006C07180001B6 |
S214006550D7B8006CA80000516678001877180018A5 |
S214006560040F0073870F0032069800040018A0007E |
S214006570C318FFFCD7B8005CC3A4005CB3FFFBCC19 |
S214006580D7A200688A400015862000140017200055 |
S2140065900016280007A6006CC3B800680A58380022 |
S2140065A06618001877180018D7B80010B3FFFE3F1B |
S2140065B00002B000A800000900162000666500185A |
S2140065C074A500180017C800B72000000002B0002D |
S2140065D0C3B8006C07180001D7B8006CC3B8005CDD |
S2140065E0070F0001D7AF005CCF1800000018980016 |
S2140065F067180018771800188700FFEF8A400027F2 |
S21400660082200026001720000016280007A6006C2F |
S214006610C3B800680A5838006618001877180018BB |
S214006620D7B80010B3FFFE210002B000A800001B80 |
S2140066306678001877180018040F0063870F000E9E |
S214006640069800040018A000CF18FFFF0018980056 |
S214006650001620006665001874A500180017C8000C |
S214006660B72000000002B000C3B8006C0718000195 |
S214006670D7B8006CA8000009001620006665001850 |
S21400668074A500180017C800B72000000002B0006C |
S214006690C3B8006C07180001D7B8006CABFFFE4407 |
S2140066A000001000C3B00018C3B1001CC3B2002025 |
S2140066B0C3B30024C3B40028C3B5002CC3B600304F |
S2140066C0C3B70034C3BF003807BD0070AFE000009A |
S2140066D00FBD0020D7BF0010D7A40020D7A50024E8 |
S2140066E0C3B80024DFB80024CFA40024B3FFFD3ACB |
S2140066F0C3A20020C3BF001007BD0020AFE000000B |
S2140067000FBD0020D7BF0010D7A40020D7A50024B7 |
S2140067107C01E0004C2166D000012000000028002B |
S214006720C3A60020C3A70024B3FFFE03D7A2001C05 |
S214006730C3A2001CC3BF001007BD0020AFE00000CE |
S2140067400FBD0020D7BF0010D7A40020D7A5002477 |
S214006750D7A60028D7A7002C07B80024D7B800185B |
S214006760C3A40020C3A50018B3FFFFE5D7A2001CF2 |
S214006770C3A2001CC3BF001007BD0020AFE000008E |
S214006780DC85000004820001AFE000000FBD0020A1 |
S214006790D7B70010D7BF0014D7A40020D7A5002471 |
S2140067A0D7A600287C01E0004C216780000120006D |
S2140067B0C3A50020C3A60024C3A70028B3FFFDDEA0 |
S2140067C00002B800C3B8002002F8C000DF000000D6 |
S2140067D000171000C3B70010C3BF001407BD002089 |
S2140067E0AFE000000FBD0020D7BF0010D7A40020E8 |
S2140067F0D7A50024D7A60028D7A7002C07B80028BE |
S214006800D7B80018C3A40020C3A50024C3A6001848 |
S214006810B3FFFFDED7A2001CC3A2001CC3BF00103C |
S21400682007BD0020AFE00000AFE000007C01F020D4 |
S21400683000014000C102000044420001AFE0000039 |
S2140068400FBD000CD7BF0008D7B00004D7B10000BA |
S214006850B000004500408000040800F086080002F2 |
S214006860B0000041ABFFFFFAB000003F00408800D8 |
S2140068708230FFFD040800F082280001A80000080E |
S214006880B00000398450FFF8020020007C01E000D0 |
S2140068904C2169C400012800B000003EA800002D6D |
S2140068A0B0000031040800F08448FFFDB000002E60 |
S2140068B08050000280510007ABFFFFF9B000002AAD |
S2140068C0040800F08448FFFDB00000278451FFFB59 |
S2140068D0A8000006B0000024040800F08448FFFD6D |
S2140068E0B00000218450FFFBA8000000040800123E |
S2140068F082080005040800598208000304080014F2 |
S2140069008208000DA8000006022020007C01E0009E |
S2140069104C216AC400012800B000001EA800000D2B |
S214006920020020007C01E0004C2169C40001280020 |
S214006930B0000018A8000007022020007C01E0003C |
S2140069404C2169C400012800B00000124442009F98 |
S214006950A8000000C3B10000C3B00004C3BF000815 |
S21400696007BD000CAFE000007C01F02000014000F5 |
S214006970C1090000452900018120FFFDC102000475 |
S214006980040900E08049FFFA040900E18049FFF8A5 |
S214006990AFE000000FBD0008D7BF0004D7B000006E |
S2140069A0449000FF02054000D10200008440000130 |
S2140069B002001000C3B00000C3BF000407BD0008FB |
S2140069C0AFE0000000000000000000000000000033 |
S2140069D000095E00000000000071310000007973BD |
S2140069E06177320000637864653433000020766691 |
S2140069F074723500006E6268677A360000006D6A51 |
S214006A0075373800002C6B696F303900002E2D6CFE |
S214006A1000700000000000000000000000000D2BC9 |
S214006A2000230000003C00000000080000000000FA |
S214006A30000000000000000000001B000000000036 |
S214006A400000000000000000000000000000000041 |
S214006A500000000000000000000000000000000031 |
S214006A600000000000000000000000000000000021 |
S214006A700000000000000000000000000000000011 |
S214006A800000000000000000000000000000000001 |
S214006A9000000000000000000000000000000000F1 |
S214006AA000000000000000000000000000000000E1 |
S214006AB000000000000000000000000000000000D1 |
S214006AC000000000000000000000000000000000C1 |
S214006AD000095E000000000000512100000059532C |
S214006AE041572200004358444524330000205646B0 |
S214006AF054522500004E4248475A260000004D4A90 |
S214006B00552F2800003B4B494F3D2900003A5F4C6B |
S214006B1000500000000000000000000000000D2AE9 |
S214006B2000270000003E00000000080000000000F3 |
S214006B30000000000000000000001B000000000035 |
S214006B400000000000000000000000000000000040 |
S214006B500000000000000000000000000000000030 |
S214006B600000000000000000000000000000000020 |
S214006B700000000000000000000000000000000010 |
S214006B800000000000000000000000000000000000 |
S214006B9000000000000000000000000000000000F0 |
S214006BA000000000000000000000000000000000E0 |
S214006BB000000000000000000000000000000000D0 |
S214006BC0000000000FBD0004D7BF0000B000008C1E |
S214006BD07C01C3FF4C21E5D400014000D500000035 |
S214006BE07C01C3FF4C21E5D800014000D500000021 |
S214006BF0B0000070B0000061C3BF000007BD000415 |
S214006C00AFE0000004020001AFE000000FBD000886 |
S214006C10D7BF0004D7B00000449000FFB000004D7E |
S214006C2004080020960800177C01C3FF4C21E5D01D |
S214006C3000014000C10900004E100700D5300000DA |
S214006C4005290004D50900007C01C3FF4C21E5D8C6 |
S214006C5000014000C109000005290001D509000017 |
S214006C60040A0050852A0002B0000013B000001C81 |
S214006C70B0000042C3B00000C3BF000407BD000858 |
S214006C80AFE000000408000D86080002B000000A0D |
S214006C90ABFFFFF70408000A86080002B0000010E9 |
S214006CA0ABFFFFF30408000886080002B000001CD3 |
S214006CB0ABFFFFEFABFFFFEE0FBD0004D7BF00003A |
S214006CC07C01C3FF4C21E5D800014000D500000040 |
S214006CD0B0000038C3BF000007BD0004AFE00000EE |
S214006CE00FBD0004D7BF00007C01C3FF4C21E5D4D4 |
S214006CF000014000C1090000040A001D812A0004AA |
S214006D0005290001D5090000B000002AA8000001EE |
S214006D10B0000048C3BF000007BD0004AFE000009D |
S214006D200FBD0004D7BF00007C01C3FF4C21E5D88F |
S214006D3000014000C1090000812000030D29000168 |
S214006D40D5090000B000001BC3BF000007BD00044B |
S214006D50AFE000007C01C3FF4C21E5D000014000FD |
S214006D60C10800007C01C3FF4C21E5DC000148009F |
S214006D70C12A0000D50A0000AFE000007C01C3FF76 |
S214006D804C21E5D000014000C10800007C01C3FF93 |
S214006D904C21E5DC00014800C10A0000D52A0000AD |
S214006DA07C0100004C21875F00015000D50A0000DE |
S214006DB0AFE000007C01F010000148007C01C3FF3A |
S214006DC04C21E5D400014000C10A0000654A0009D4 |
S214006DD0012A48007C01C3FF4C21E5D80001400091 |
S214006DE0C10A0000654A0002012A48007C01C3FF70 |
S214006DF04C21E5D000014000D5090000AFE00000BE |
S214006E00040B07207C01F010000140000409001E5E |
S214006E10040A0050D50B0000050800040D4A0001C6 |
S214006E208540FFFC050800C00D2900018520FFF8FD |
S214006E30AFE000007C01F010000140000409001DD6 |
S214006E40040A0050C10B0200D50B00000508000420 |
S214006E500D4A00018540FFFB050800C00D29000112 |
S214006E608520FFF7040B0720040A0050D50B00000E |
S214006E70050800040D4A00018540FFFCAFE0000055 |
S214006E80AFE000007C01F03000014000C1020000CD |
S214006E9044420001AFE000007C01F03000014000F9 |
S214006EA0C1090000452900018120FFFDC102000440 |
S214006EB0AFE000007C01F03000014000C102000895 |
S214006EC044420001AFE000007C01F03000014000C9 |
S214006ED0C1090008452900018120FFFDD504000CEA |
S214006EE0AFE000007C01F0304C21100000014000B3 |
S214006EF0C102000044420001AFE000007C01F03017 |
S214006F004C21100000014000C10900004529000185 |
S214006F108120FFFDC1020004AFE000007C01F030DC |
S214006F204C21100000014000C1020008444200014C |
S214006F30AFE000007C01F0304C2110000001400062 |
S214006F40C1090008452900018120FFFDD504000C79 |
S214006F50AFE000007C01000F4C21424000014000E1 |
S214006F607C01F04000014800C12A0000454A00208C |
S214006F70854000040D0800018500FFFB04020000A8 |
S214006F80A8000001C122000CAFE000000FBD0018F1 |
S214006F90D7BF0014D7B00010D7B1000CD7B2000886 |
S214006FA0D7B30004D7B400000080800000A088009B |
S214006FB07C01C00000C1900000E098000408007248 |
S214006FC082080004040800778208001C040200FF00 |
S214006FD0A800003400001000826000327C01F040FF |
S214006FE00001400004090001D5090004D51100087D |
S214006FF004090001D5090000C10200004449001040 |
S2140070008120FFFD44490008852000267C01F048C9 |
S2140070100001400004090200C10A0000D64A000030 |
S21400702005080004065200040D2900048520FFFA16 |
S214007030063100010E730001ABFFFFE600001000F2 |
S214007040826000187C01F04800014000040902003C |
S214007050C24A0000D50A00000652000405080004D3 |
S2140070600D2900048520FFFA7C01F0400001400055 |
S21400707004090001D5090004D5110008040900051B |
S214007080D5090000C1020000444900108120FFFD20 |
S2140070904449000885200003063100010E730001F4 |
S2140070A0ABFFFFE6C3B40000C3B30004C3B20008DE |
S2140070B0C3B1000CC3B00010C3BF001407BD001856 |
S2140070C0AFE000000FBD0010D7B00000D7B100043D |
S2140070D0D7B20008D7BF000C7C01C3FF4C21DA04EE |
S2140070E000012000B3FFFACB000090000410000A55 |
S2140070F00E10000104040016B3FFFF8E7C01000C86 |
S2140071004C213500000188000E310001B3FFFF75E9 |
S2140071108440000B8620FFFC7C01C3FF4C21DA294B |
S21400712000012000B3FFFABB8600FFF17C01C3FF1D |
S2140071304C21DA3F00012000B3FFFAB6A800000F8A |
S214007140B3FFFF6E040800068448000C0404000623 |
S214007150B3FFFF7804040063B3FFFF76B3FFFF6757 |
S214007160844000060410000466520008B3FFFF6364 |
S2140071704A4290000E1000018600FFFB001210002D |
S214007180C3B00000C3B10004C3B20008C3BF000C04 |
S21400719007BD0010AFE000000FBD0018D7B000001C |
S2140071A0D7B10004D7B20008D7B3000CD7B400108C |
S2140071B0D7BF001400048000000588007C01C000D2 |
S2140071C0000140004906900000079800040800727D |
S2140071D081100004040800778110001804020001E2 |
S2140071E0A800002B826000130E73000104040072D6 |
S2140071F0B3FFFF50041400200E9400086A342000E9 |
S214007200448400FFB3FFFF4B8680FFFB063100017E |
S214007210B3FFFF3A8440001E041402000E940001DF |
S214007220B3FFFF36DE420000065200018680FFFBF9 |
S214007230ABFFFFEC00001000A800001582600013F2 |
S2140072400E73000104040077B3FFFF3A0414002015 |
S2140072500E9400086A342000448400FFB3FFFF3514 |
S2140072608680FFFB06310001041402000E94000124 |
S214007270D2440000B3FFFF2F065200018680FFFBBA |
S214007280B3FFFF1E84400002ABFFFFEC00001000BF |
S214007290C3B00000C3B10004C3B20008C3B3000CFF |
S2140072A0C3B40010C3BF001407BD0018AFE0000051 |
S2140072B045434F3332203E20000A0A45434F3332BF |
S2140072C0204D616368696E65204D6F6E69746F72DC |
S2140072D020312E310A0A0000C3FFC1ABE00004D003 |
S2140072E0E0000AF8C3FFC1A9E0000504E0000BC4F3 |
S2140072F0C3FFC1A7E0000528E0000C74C3FFC1A5CA |
S214007300E000055CE0000DA4C3FFC1A3E00005A0FB |
S214007310E0000F28C3FFC1A1E00005D4E0000FB8CD |
S214007320C3FFC19FE0000608E0001070C3FFC19DC8 |
S214007330E000063CE000110CC3FFC20AE000067045 |
S214007340E00015D8C3FFC19BE00006A4E000167C51 |
S214007350C3FFC199E00006E8E0001810C3FFC1961D |
S214007360E000072CE0001AB4C3FFC193E0000770EA |
S214007370E0001BE8C3FFC190E00007B4E0001D2456 |
S214007380C3FFC18EE00007F8E0001E60C3FFC1899E |
S214007390E000084CE00021D0C3FFC184E000087084 |
S2140073A0E000224000000011202020202020546809 |
S2140073B06973206576656E742077696C6C206E6FD5 |
S2140073C07420616C746572207468652073746174CF |
S2140073D065206F6620746865204350552E0A004E5F |
S2140073E04F54453A202573202573206F63637572CA |
S2140073F0726564207768696C652065786563757466 |
S214007400696E672074686520636F6D6D616E642EAB |
S2140074100A004100416E00746F6F206D616E792026 |
S214007420746F6B656E73206F6E206C696E650A00F4 |
S21400743020090A00626F6F74006C6F61640074004C |
S2140074406D62006D68006D77006400720023007343 |
S2140074500063006200750061002B0068656C7000B8 |
S214007460696C6C6567616C206469736B206E756D02 |
S2140074706265720A00696C6C6567616C2073657280 |
S21400748069616C206C696E65206E756D6265720A46 |
S21400749000544C422073656C6563746F7220697388 |
S2140074A0206E6F74206F6E65206F66202770272011 |
S2140074B06F72202766270A0066007000696C6C658C |
S2140074C067616C20544C4220696E6465780A0045FA |
S2140074D06E7472794C6F28332920253038580A008C |
S2140074E0456E747279486928322920253038580A42 |
S2140074F000496E64657828312920202025303858C8 |
S2140075000A00544C425B253032645D2020202070F7 |
S214007510616765202025303858202020206672615B |
S2140075206D652020253038582020256320202563CF |
S2140075300A00253038583A2020253032580A0025CF |
S2140075403038583A2020253034580A00253038582C |
S2140075503A2020253038580A002E002000253032E8 |
S2140075605800253038583A20200024252D32642033 |
S21400757020253038580A00696C6C6567616C20728B |
S21400758065676973746572206E756D6265720A0050 |
S21400759024252D3264202025303858202020202015 |
S2140075A000696C6C6567616C20646174610A002513 |
S2140075B02D3335733A20257320282573290A006C4D |
S2140075C061737420696E746572727570742061637D |
S2140075D06B6E6F776C6564676564202020202020C2 |
S2140075E020203A20253032582020282573290A00EA |
S2140075F06F6C6420696E7465727275707420656E47 |
S21400760061626C6520202020202020202020202061 |
S2140076102020203A20257320282573290A0070721E |
S2140076206576696F757320696E74657272757074AD |
S21400763020656E61626C652020202020202020209E |
S214007640203A20257320282573290A00646973616F |
S214007650626C656400656E61626C65640063757279 |
S21400766072656E7420696E746572727570742065CA |
S2140076706E61626C652020202020202020202020A3 |
S2140076803A20257320282573290A006F6C6420751C |
S214007690736572206D6F64652020202020202020D6 |
S2140076A020202020202020202020202020203A20BB |
S2140076B0257320282573290A0070726576696F7510 |
S2140076C0732075736572206D6F64652020202020FE |
S2140076D02020202020202020202020203A20257333 |
S2140076E020282573290A006B65726E656C00757319 |
S2140076F065720063757272656E74207573657220AC |
S2140077006D6F64652020202020202020202020204F |
S2140077102020202020203A20257320282573290A9F |
S21400772000524F4D0052414D006F6666006F6E204E |
S21400773000696E7465727275707420766563746F16 |
S21400774072202020202020202020202020202020E2 |
S214007750202020203A20257320282573290A00425D |
S2140077607265616B20617420253038580A00253018 |
S21400777038583A2020253038582020202025730AF3 |
S21400778000696C6C6567616C20636F756E740A00C7 |
S21400779025730A0041534D202320253038583A20BF |
S2140077A000696C6C6567616C2061646472657373F4 |
S2140077B00A00616464203D20253038582C207375FB |
S2140077C062203D20253038580A00696C6C65676178 |
S2140077D06C207365636F6E64206E756D6265720AE9 |
S2140077E000696C6C6567616C206669727374206EE4 |
S2140077F0756D6265720A006E6F2068656C70206138 |
S2140078007661696C61626C6520666F7220272573ED |
S214007810272C20736F7272790A00256300202000DF |
S2140078205053572020002020202020787878782079 |
S2140078302056202055504F202049504F20204941A7 |
S214007840434B2020204D41534B0A000A002D2D2D7E |
S2140078502D2D2D2D2D00253038580042726B2020FE |
S2140078600050432020202530385820202020205B40 |
S21400787050435D2020202530385820202025730ACC |
S214007880002020626F6F74203C6E3E202020202057 |
S21400789020202020206C6F616420616E6420657853 |
S2140078A065637574652066697273742073656374A6 |
S2140078B06F72206F66206469736B203C6E3E0A0010 |
S2140078C020206C6F6164203C6E3E2020202020200B |
S2140078D0202020206C6F616420616E20532D72651D |
S2140078E0636F72642066696C652066726F6D2073C4 |
S2140078F0657269616C206C696E65203C6E3E0A009C |
S21400790020207420203C693E2066203C646174611F |
S2140079103E20202073657420544C4220636F6E74A2 |
S214007920656E7473206174203C693E20746F206617 |
S21400793072616D65203C646174613E0A00202074AB |
S21400794020203C693E2070203C646174613E20200B |
S2140079502073657420544C4220636F6E74656E7499 |
S21400796073206174203C693E20746F2070616765E7 |
S214007970203C646174613E0A0020207420203C692B |
S2140079803E20202020202020202020202073686FEA |
S2140079907720544C4220636F6E74656E747320615A |
S2140079A074203C693E0A00202074202020202020DD |
S2140079B0202020202020202020202073686F772081 |
S2140079C0544C4220636F6E74656E74730A002020F8 |
S2140079D06D62203C616464723E203C646174613E6A |
S2140079E02020736574206D656D6F727920627974DE |
S2140079F065206174203C616464723E20746F203C94 |
S214007A00646174613E0A0020206D62203C616464FB |
S214007A10723E20202020202020202073686F7720B0 |
S214007A206D656D6F72792062797465206174203C93 |
S214007A30616464723E0A0020206D622020202020AF |
S214007A40202020202020202020202073686F7720F0 |
S214007A506D656D6F7279206279746520617420504F |
S214007A60430A0020206D68203C616464723E203C1E |
S214007A70646174613E2020736574206D656D6F725D |
S214007A80792068616C66776F7264206174203C614F |
S214007A906464723E20746F203C646174613E0A0028 |
S214007AA020206D68203C616464723E2020202020E7 |
S214007AB02020202073686F77206D656D6F727920A7 |
S214007AC068616C66776F7264206174203C616464E0 |
S214007AD0723E0A0020206D682020202020202020D2 |
S214007AE0202020202020202073686F77206D656D71 |
S214007AF06F72792068616C66776F7264206174209B |
S214007B0050430A0020206D77203C616464723E205A |
S214007B103C646174613E2020736574206D656D6FF2 |
S214007B20727920776F7264206174203C616464729D |
S214007B303E20746F203C646174613E0A0020206D14 |
S214007B4077203C616464723E202020202020202084 |
S214007B502073686F77206D656D6F727920776F720E |
S214007B6064206174203C616464723E0A0020206DCB |
S214007B7077202020202020202020202020202020A9 |
S214007B802073686F77206D656D6F727920776F72DE |
S214007B90642061742050430A0020206420203C6149 |
S214007BA06464723E203C636E743E20202064756DD3 |
S214007BB070203C636E743E20627974657320737423 |
S214007BC0617274696E67206174203C616464723E01 |
S214007BD00A0020206420203C616464723E2020203D |
S214007BE020202020202064756D70203235362062DB |
S214007BF079746573207374617274696E672061743A |
S214007C00203C616464723E0A00202064202020200C |
S214007C102020202020202020202020202064756D79 |
S214007C207020323536206279746573207374617201 |
S214007C3074696E672061742050430A002020722009 |
S214007C40203C7265673E203C646174613E202020C3 |
S214007C50736574207265676973746572203C72651B |
S214007C60673E20746F203C646174613E0A002020E9 |
S214007C707220203C7265673E202020202020202095 |
S214007C80202073686F772072656769737465722049 |
S214007C903C7265673E0A00202072202020202020AB |
S214007CA0202020202020202020202073686F77208E |
S214007CB0616C6C207265676973746572730A002064 |
S214007CC0207020203C646174613E2020202020200B |
S214007CD02020207365742050535720746F203C6416 |
S214007CE06174613E0A002020702020202020202081 |
S214007CF02020202020202020202073686F7720500E |
S214007D0053570A0020202320203C616464723E20E2 |
S214007D1020202020202020207365742050432074CB |
S214007D206F203C616464723E0A00202023202020DD |
S214007D3020202020202020202020202020207368A3 |
S214007D406F772050430A0020207320203C636E7417 |
S214007D503E2020202020202020202073696E676C83 |
S214007D60652D73746570203C636E743E20696E7377 |
S214007D707472756374696F6E730A00202073202016 |
S214007D80202020202020202020202020202020739B |
S214007D90696E676C652D73746570206F6E652069FB |
S214007DA06E737472756374696F6E0A0020206320A8 |
S214007DB0203C636E743E202020202020202020209F |
S214007DC0636F6E74696E7565206578656375746932 |
S214007DD06F6E203C636E743E2074696D65730A0096 |
S214007DE0202063202020202020202020202020204B |
S214007DF020202020636F6E74696E75652065786537 |
S214007E00637574696F6E0A0020206220203C6164EE |
S214007E1064723E20202020202020202073657420BD |
S214007E20627265616B206174203C616464723E0A14 |
S214007E30002020622020202020202020202020201B |
S214007E402020202020726573657420627265616B45 |
S214007E500A0020207520203C616464723E203C634A |
S214007E606E743E202020756E617373656D626C655E |
S214007E70203C636E743E20696E7374727320737454 |
S214007E80617274696E67206174203C616464723E3E |
S214007E900A0020207520203C616464723E20202069 |
S214007EA0202020202020756E617373656D626C65DE |
S214007EB020313620696E7374727320737461727425 |
S214007EC0696E67206174203C616464723E0A00201B |
S214007ED02075202020202020202020202020202048 |
S214007EE0202020756E617373656D626C6520313677 |
S214007EF020696E73747273207374617274696E672E |
S214007F002061742050430A0020206120203C6164D8 |
S214007F1064723E202020202020202020617373657C |
S214007F206D626C65207374617274696E672061742B |
S214007F30203C616464723E0A0020206120202020DC |
S214007F402020202020202020202020202061737345 |
S214007F50656D626C65207374617274696E6720610A |
S214007F60742050430A0020202B20203C6E756D3173 |
S214007F703E203C6E756D323E202061646420616E4A |
S214007F8064207375627472616374203C6E756D3123 |
S214007F903E20616E64203C6E756D323E0A002020E5 |
S214007FA068656C70203C636D643E20202020202095 |
S214007FB0202073686F772068656C7020666F72206B |
S214007FC03C636D643E0A00202068656C70202020AB |
S214007FD0202020202020202020202073686F77205B |
S214007FE061206C697374206F6620636F6D6D616EBF |
S214007FF064730A0074797065202768656C70203C8D |
S214008000636D643E2720746F206765742068656C16 |
S2140080107020666F72203C636D643E0A002020620A |
S2140080206F6F7420202020626F6F7473747261709B |
S2140080302066726F6D206469736B0A0020206C6F77 |
S2140080406164202020206C6F61642066726F6D2052 |
S21400805073657269616C206C696E650A0020207415 |
S2140080602020202020202073686F772F73657420CF |
S214008070544C4220636F6E74656E74730A00202041 |
S2140080806D6220202020202073686F772F73657420 |
S214008090206D656D6F727920627974650A00202004 |
S2140080A06D6820202020202073686F772F736574FA |
S2140080B0206D656D6F72792068616C66776F72648B |
S2140080C00A0020206D7720202020202073686F77FC |
S2140080D02F736574206D656D6F727920776F72648B |
S2140080E00A002020642020202020202064756D7047 |
S2140080F0206D656D6F72790A002020722020202086 |
S21400810020202073686F772F736574207265676907 |
S214008110737465720A002020702020202020202002 |
S21400812073686F772F736574205053570A002020AA |
S214008130232020202020202073686F772F736574FB |
S2140081402050430A00202073202020202020207367 |
S214008150696E676C652D737465700A002020632055 |
S214008160202020202020636F6E74696E756520665F |
S214008170726F6D20627265616B706F696E740A0053 |
S214008180202062202020202020207365742F726516 |
S21400819073657420627265616B706F696E740A0035 |
S2140081A020207520202020202020756E61737365A6 |
S2140081B06D626C650A00202061202020202020208F |
S2140081C0617373656D626C650A0020202B20202089 |
S2140081D02020202061646420616E642073756274C0 |
S2140081E0726163740A00202068656C70202020206D |
S2140081F06765742068656C700A0076616C69642037 |
S214008200636F6D6D616E6473206172653A0A00007B |
S214008210C3FFD24A0000000700000000C3FFD2469A |
S2140082200000000702000000C3FFD2420000000763 |
S21400823004000000C3FFD23D000000060600000058 |
S214008240C3FFD2390000000708000000C3FFD23485 |
S214008250000000060A000000C3FFD230000000073E |
S2140082600C000000C3FFD22B000000060E0000002A |
S214008270C3FFD2270000000610000000C3FFD22470 |
S2140082800000000612000000C3FFD2200000000617 |
S21400829014000000C3FFD21B0000000616000000FA |
S2140082A0C3FFD2170000000618000000C3FFD21359 |
S2140082B0000000061A000000C3FFD20F00000006F0 |
S2140082C01C000000C3FFD20A000000021F000000CE |
S2140082D0C3FFD2060000000820000000C3FFD20241 |
S2140082E00000000821000000C3FFD1FE00000008C7 |
S2140082F022000000C3FFD1F90000000823000000A0 |
S214008300C3FFD1F50000000824000000C3FFD1F031 |
S2140083100000000825000000C3FFD1EC00000008A4 |
S21400832026000000C3FFD1E7000000082700000079 |
S214008330C3FFD1E30000000828000000C3FFD1DE21 |
S2140083400000000829000000C3FFD1DC000000097F |
S2140083502A000000C3FFD1D90000000A2B0000004D |
S214008360C3FFD1D5000000092C000000C3FFD1D008 |
S2140083700000000A2D000000C3FFD1CB0000000063 |
S2140083802E000000C3FFD1C7000000002F00000031 |
S214008390C3FFD1C30000000430000000C3FFD1BFFC |
S2140083A00000000431000000C3FFD1BA0000000442 |
S2140083B032000000C3FFD1B6000000043300000006 |
S2140083C0C3FFD1B10000000434000000C3FFD1ADEC |
S2140083D00000000435000000C3FFD1A9000000041F |
S2140083E036000000C3FFD1A50000000437000000DF |
S2140083F0C3FFD1A00000000138000000C3FFD19BDE |
S2140084000000000139000000C3FFD1970000000003 |
S2140084103A000000C3FFD192000000003B000000BD |
S214008420C3FFD18D000000003C000000C3FFD188D0 |
S214008430000000003D0000007462776900746272FC |
S21400844069007462777200746273006D76747300EC |
S2140084506D76667300737462007374680073747765 |
S214008460006C646275006C6462006C646875006C15 |
S2140084706468006C647700726678007472617000DD |
S2140084806A616C72006A616C006A72006A006267F8 |
S21400849074750062677400626765750062676500E0 |
S2140084A0626C747500626C7400626C657500626C58 |
S2140084B06500626E6500626571006C6468690073D1 |
S2140084C0617200736C7200736C6C00786E6F720071 |
S2140084D0786F72006F7200616E640072656D750071 |
S2140084E072656D006469767500646976006D756CFA |
S2140084F075006D756C007375620061646400000041 |
S214008500C3FFD388C3FFD37DC3FFD364C3FFD34960 |
S214008510C3FFD333C3FFD322C3FFD311C3FFD2F9A4 |
S214008520C3FFD2DCC3FFD2C6C3FFD2ADE000290C26 |
S214008530E0002998E0002A64E0002B3CE0002C389C |
S214008540E0002D40E0002E18E0002F80E00030F420 |
S214008550E000323CE000332C20090A2C00746172E3 |
S2140085606765742063616E6E6F7420626520726545 |
S214008570616368656400746172676574206973205E |
S2140085806E6F7420616C69676E656400696D6D65F9 |
S21400859064696174652076616C7565206F757420FA |
S2140085A06F662072616E676500696C6C6567616CEA |
S2140085B020696D6D6564696174652076616C7565AA |
S2140085C000696C6C6567616C2072656769737465B9 |
S2140085D07200746F6F20666577206F706572616ECB |
S2140085E064730065786365737320746F6B656E7370 |
S2140085F0206F6E206C696E6500756E6B6E6F776EA1 |
S21400860020696E737472756374696F6E20666F721C |
S2140086106D617400756E6B6E6F776E20696E737425 |
S21400862072756374696F6E206E616D6500656D703E |
S2140086307479206C696E6500746F6F206D616E7959 |
S21400864020746F6B656E73206F6E206C696E6500AC |
S214008650E00038A8E00038C4E00038E8E000390C54 |
S214008660E000393CE000396CE00039A0E0003A1048 |
S214008670E0003A80E0003AB8E0003AD8696C6C65F1 |
S21400868067616C20656E74727920696E20696E73FE |
S2140086907472756374696F6E207461626C650A002B |
S2140086A03F3F3F00252D37732024256400252D37B6 |
S2140086B073202425642C2425642C25303858002566 |
S2140086C02D3773202425642C2425642C242564004F |
S2140086D02B002D00252D3773202425642C2425649B |
S2140086E02C25732530345800252D37732024256417 |
S2140086F02C2425642C2530345800252D377320244F |
S21400870025642C2530385800252D37732024256401 |
S2140087102C2530345800252D377320253038580046 |
S214008720252D377300000000E00041CCE0003F1C20 |
S214008730E0003F80E0004004E00041B8E00041CCAB |
S214008740E00041B8E00040A0E0004118E0004178B9 |
S214008750436F6E6E656374696F6E20746F206C6F06 |
S21400876061642073657276657220636C6F736564EE |
S2140087702E0A004572726F723A20756E6B6E6F77B6 |
S2140087806E2074797065206F6620532D7265636F56 |
S2140087907264210A004572726F723A2077726F6EA9 |
S2140087A06720636865636B73756D20696E20532D53 |
S2140087B07265636F7264210A004572726F723A20A6 |
S2140087C0696E636F6E73697374656E742062797414 |
S2140087D06520636F756E7420696E20532D72656315 |
S2140087E06F7264210A004572726F723A206D616C76 |
S2140087F0666F726D656420532D7265636F726421B7 |
S2140088000A0025730A004572726F723A20746F6F01 |
S214008810206D616E7920636861726163746572733E |
S21400882020696E20532D7265636F7264210A0043BF |
S2140088306F6E6E656374656420746F206C6F616420 |
S214008840207365727665722E0A00556E61626C65DD |
S21400885020746F2065737461626C69736820636F3F |
S2140088606E6E656374696F6E20746F206C6F6164E2 |
S214008870207365727665722E0A005265717565738F |
S214008880742074696D6564206F75742E2E2E0A0030 |
S214008890547279696E6720746F20636F6E6E6563BD |
S2140088A07420746F206C6F616420736572766572D5 |
S2140088B02E2E2E0A000000004D4252207369676E6D |
S2140088C06174757265206D697373696E67210A003D |
S2140088D04469736B206572726F72210A0044697373 |
S2140088E06B20776974682030782530385820736597 |
S2140088F063746F727320666F756E642C20626F6F80 |
S21400890074696E672E2E2E0A004469736B206E6F94 |
S2140089107420666F756E64210A000000C3FFD9A636 |
S214008920C3FFD988C3FFD967C3FFD949C3FFD93668 |
S214008930C3FFD924C3FFD924C3FFD924C3FFD91545 |
S214008940C3FFD924C3FFD924C3FFD924C3FFD92426 |
S214008950C3FFD924C3FFD905C3FFD924C3FFD8EF6B |
S214008960C3FFD8D1C3FFD8B0C3FFD893C3FFD8780E |
S214008970C3FFD865C3FFD851C3FFD83BC3FFD82178 |
S214008980C3FFD804C3FFD7F2C3FFD7F2C3FFD7F2A3 |
S214008990C3FFD7F2C3FFD7F2C3FFD7F2010101012D |
S2140089A001010101010101010101010101010101B2 |
S2140089B0010101010101010101010101020202029E |
S2140089C00202020202020304030401000101010183 |
S2140089D0010101010101010101010101E00044C0A2 |
S2140089E0E00044D4E00044E8E00044FCE000451029 |
S2140089F0E0004524E0004538E000454CE0004560D6 |
S214008A00E0004574E0004660E0004678E00046FC82 |
S214008A10E000474C756E6578706563746564202564 |
S214008A2073206F636375727265640A0063616E6EAD |
S214008A306F742073696E676C652D7374657020693A |
S214008A406E737472756374696F6E207769746820CC |
S214008A506F70636F6465203078253032580A006383 |
S214008A60616E6E6F7420636F6D7075746520636FD2 |
S214008A706E646974696F6E20636F64652025640A8E |
S214008A80003C657863657074696F6E206E756D6204 |
S214008A906572206F7574206F6620626F756E6473E2 |
S214008AA03E00756E6B6E6F776E20657863657074CA |
S214008AB0696F6E0070726976696C656765642061BF |
S214008AC064647265737320657863657074696F6E2D |
S214008AD000696C6C6567616C2061646472657373B1 |
S214008AE020657863657074696F6E00544C42206927 |
S214008AF06E76616C696420657863657074696F6E04 |
S214008B0000544C42207772697465206578636570FE |
S214008B1074696F6E00544C42206D697373206578DB |
S214008B2063657074696F6E007472617020696E732D |
S214008B307472756374696F6E2065786365707469A6 |
S214008B406F6E0064697669646520696E7374727509 |
S214008B506374696F6E20657863657074696F6E0004 |
S214008B6070726976696C6567656420696E73747285 |
S214008B70756374696F6E20657863657074696F6E6F |
S214008B8000696C6C6567616C20696E7374727563DE |
S214008B9074696F6E20657863657074696F6E0062C5 |
S214008BA075732074696D656F75742065786365707C |
S214008BB074696F6E0074696D657220696E74657293 |
S214008BC072757074006469736B20696E7465727276 |
S214008BD075707400756E6B6E6F776E20696E746557 |
S214008BE07272757074006B6579626F617264206969 |
S214008BF06E74657272757074007465726D696E61FC |
S214008C006C203120726563656976657220696E74C2 |
S214008C10657272757074007465726D696E616C2031 |
S214008C2031207472616E736D697474657220696E3A |
S214008C3074657272757074007465726D696E616CBD |
S214008C40203020726563656976657220696E74658A |
S214008C507272757074007465726D696E616C203026 |
S214008C60207472616E736D697474657220696E74B7 |
S214008C70657272757074000020000D00E00057CC1D |
S214008C80E00057CCE00057CCE00057CCE00057CCD3 |
S214008C90303132333435363738396162636465666D |
S214008CA00030313233343536373839414243444563 |
S214008CB046000000547279696E6720746F20636FF7 |
S214008CC06E6E65637420746F206469736B207365C1 |
S214008CD0727665722E2E2E0A005265717565737453 |
S214008CE02074696D6564206F75742E2E2E0A0055EB |
S214008CF06E61626C6520746F2065737461626C6966 |
S214008D00736820636F6E6E656374696F6E20746F30 |
S214008D10206469736B207365727665722E0A000094 |
S804000000FB |
/monitor/monitor-digilent/boot.c
0,0 → 1,47
/* |
* boot.c -- bootstrap from disk |
*/ |
|
|
#include "common.h" |
#include "stdarg.h" |
#include "romlib.h" |
#include "boot.h" |
#include "cpu.h" |
#include "mmu.h" |
#include "start.h" |
|
|
void boot(int dskno) { |
Word capacity; |
Byte sig1, sig2; |
|
capacity = dskcap(dskno); |
if (capacity == 0) { |
printf("Disk not found!\n"); |
return; |
} |
printf("Disk with 0x%08X sectors found, booting...\n", capacity); |
if (dskio(dskno, 'r', 0, PHYS_BOOT, 1) != 0) { |
printf("Disk error!\n"); |
return; |
} |
sig1 = mmuReadByte(VIRT_BOOT + 512 - 2); |
sig2 = mmuReadByte(VIRT_BOOT + 512 - 1); |
if (sig1 != 0x55 || sig2 != 0xAA) { |
printf("MBR signature missing!\n"); |
return; |
} |
/* |
* Boot convention: |
* $16 disk number of boot disk |
* $17 start sector number of disk or partition to boot |
* $18 total number of sectors of disk or partition to boot |
*/ |
cpuSetReg(16, dskno); |
cpuSetReg(17, 0); |
cpuSetReg(18, capacity); |
cpuSetReg(29, TOS_BOOT); |
cpuSetPC(VIRT_BOOT); |
cpuRun(); |
} |
/monitor/monitor-digilent/boot.h
0,0 → 1,18
/* |
* boot.h -- bootstrap from disk |
*/ |
|
|
#ifndef _BOOT_H_ |
#define _BOOT_H_ |
|
|
#define PHYS_BOOT 0x00000000 /* where to load the bootstrap */ |
#define VIRT_BOOT 0xC0000000 /* where to start the bootstrap */ |
#define TOS_BOOT 0xC0001000 /* top of stack for bootstrap */ |
|
|
void boot(int dskno); |
|
|
#endif /* _BOOT_H_ */ |
/monitor/monitor-digilent/monitor.bin
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
monitor/monitor-digilent/monitor.bin
Property changes :
Added: svn:mime-type
## -0,0 +1 ##
+application/octet-stream
\ No newline at end of property
Index: monitor/monitor-digilent/command.c
===================================================================
--- monitor/monitor-digilent/command.c (nonexistent)
+++ monitor/monitor-digilent/command.c (revision 16)
@@ -0,0 +1,887 @@
+/*
+ * command.c -- command interpreter
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "getline.h"
+#include "command.h"
+#include "asm.h"
+#include "disasm.h"
+#include "load.h"
+#include "boot.h"
+#include "cpu.h"
+#include "mmu.h"
+#include "start.h"
+
+
+#define MAX_TOKENS 10
+
+
+typedef struct {
+ char *name;
+ void (*hlpProc)(void);
+ void (*cmdProc)(char *tokens[], int n);
+} Command;
+
+extern Command commands[];
+extern int numCommands;
+
+
+static void help(void) {
+ printf("valid commands are:\n");
+ printf(" help get help\n");
+ printf(" + add and subtract\n");
+ printf(" a assemble\n");
+ printf(" u unassemble\n");
+ printf(" b set/reset breakpoint\n");
+ printf(" c continue from breakpoint\n");
+ printf(" s single-step\n");
+ printf(" # show/set PC\n");
+ printf(" p show/set PSW\n");
+ printf(" r show/set register\n");
+ printf(" d dump memory\n");
+ printf(" mw show/set memory word\n");
+ printf(" mh show/set memory halfword\n");
+ printf(" mb show/set memory byte\n");
+ printf(" t show/set TLB contents\n");
+ printf(" load load from serial line\n");
+ printf(" boot bootstrap from disk\n");
+ printf("type 'help ' to get help for \n");
+}
+
+
+static void help00(void) {
+ printf(" help show a list of commands\n");
+ printf(" help show help for \n");
+}
+
+
+static void help01(void) {
+ printf(" + add and subtract and \n");
+}
+
+
+static void help02(void) {
+ printf(" a assemble starting at PC\n");
+ printf(" a assemble starting at \n");
+}
+
+
+static void help03(void) {
+ printf(" u unassemble 16 instrs starting at PC\n");
+ printf(" u unassemble 16 instrs starting at \n");
+ printf(" u unassemble instrs starting at \n");
+}
+
+
+static void help04(void) {
+ printf(" b reset break\n");
+ printf(" b set break at \n");
+}
+
+
+static void help05(void) {
+ printf(" c continue execution\n");
+ printf(" c continue execution times\n");
+}
+
+
+static void help06(void) {
+ printf(" s single-step one instruction\n");
+ printf(" s single-step instructions\n");
+}
+
+
+static void help07(void) {
+ printf(" # show PC\n");
+ printf(" # set PC to \n");
+}
+
+
+static void help08(void) {
+ printf(" p show PSW\n");
+ printf(" p set PSW to \n");
+}
+
+
+static void help09(void) {
+ printf(" r show all registers\n");
+ printf(" r show register \n");
+ printf(" r set register to \n");
+}
+
+
+static void help10(void) {
+ printf(" d dump 256 bytes starting at PC\n");
+ printf(" d dump 256 bytes starting at \n");
+ printf(" d dump bytes starting at \n");
+}
+
+
+static void help11(void) {
+ printf(" mw show memory word at PC\n");
+ printf(" mw show memory word at \n");
+ printf(" mw set memory word at to \n");
+}
+
+
+static void help12(void) {
+ printf(" mh show memory halfword at PC\n");
+ printf(" mh show memory halfword at \n");
+ printf(" mh set memory halfword at to \n");
+}
+
+
+static void help13(void) {
+ printf(" mb show memory byte at PC\n");
+ printf(" mb show memory byte at \n");
+ printf(" mb set memory byte at to \n");
+}
+
+
+static void help14(void) {
+ printf(" t show TLB contents\n");
+ printf(" t show TLB contents at \n");
+ printf(" t p set TLB contents at to page \n");
+ printf(" t f set TLB contents at to frame \n");
+}
+
+
+static void help15(void) {
+ printf(" load load an S-record file from serial line \n");
+}
+
+
+static void help16(void) {
+ printf(" boot load and execute first sector of disk \n");
+}
+
+
+static Bool getHexNumber(char *str, Word *valptr) {
+ char *end;
+
+ *valptr = strtoul(str, &end, 16);
+ return *end == '\0';
+}
+
+
+static Bool getDecNumber(char *str, int *valptr) {
+ char *end;
+
+ *valptr = strtoul(str, &end, 10);
+ return *end == '\0';
+}
+
+
+static void showPC(void) {
+ Word pc, psw;
+ Word instr;
+
+ pc = cpuGetPC();
+ psw = cpuGetPSW();
+ instr = mmuReadWord(pc);
+ printf("PC %08X [PC] %08X %s\n",
+ pc, instr, disasm(instr, pc));
+}
+
+
+static void showBreak(void) {
+ Word brk;
+
+ brk = cpuGetBreak();
+ printf("Brk ");
+ if (cpuTestBreak()) {
+ printf("%08X", brk);
+ } else {
+ printf("--------");
+ }
+ printf("\n");
+}
+
+
+static void showPSW(void) {
+ Word psw;
+ int i;
+
+ psw = cpuGetPSW();
+ printf(" xxxx V UPO IPO IACK MASK\n");
+ printf("PSW ");
+ for (i = 31; i >= 0; i--) {
+ if (i == 27 || i == 26 || i == 23 || i == 20 || i == 15) {
+ printf(" ");
+ }
+ printf("%c", psw & (1 << i) ? '1' : '0');
+ }
+ printf("\n");
+}
+
+
+static void doHelp(char *tokens[], int n) {
+ int i;
+
+ if (n == 1) {
+ help();
+ } else if (n == 2) {
+ for (i = 0; i < numCommands; i++) {
+ if (strcmp(commands[i].name, tokens[1]) == 0) {
+ (*commands[i].hlpProc)();
+ return;
+ }
+ }
+ printf("no help available for '%s', sorry\n", tokens[1]);
+ } else {
+ help00();
+ }
+}
+
+
+static void doArith(char *tokens[], int n) {
+ Word num1, num2, num3, num4;
+
+ if (n == 3) {
+ if (!getHexNumber(tokens[1], &num1)) {
+ printf("illegal first number\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &num2)) {
+ printf("illegal second number\n");
+ return;
+ }
+ num3 = num1 + num2;
+ num4 = num1 - num2;
+ printf("add = %08X, sub = %08X\n", num3, num4);
+ } else {
+ help01();
+ }
+}
+
+
+static void doAssemble(char *tokens[], int n) {
+ Word addr;
+ Word psw;
+ char prompt[30];
+ char *line;
+ char *msg;
+ Word instr;
+
+ if (n == 1) {
+ addr = cpuGetPC();
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ } else {
+ help02();
+ return;
+ }
+ addr &= ~0x00000003;
+ psw = cpuGetPSW();
+ while (1) {
+ sprintf(prompt, "ASM # %08X: ", addr);
+ line = getLine(prompt);
+ if (*line == '\0' || *line == '\n') {
+ break;
+ }
+ addHist(line);
+ msg = asmInstr(line, addr, &instr);
+ if (msg != NULL) {
+ printf("%s\n", msg);
+ } else {
+ mmuWriteWord(addr, instr);
+ addr += 4;
+ }
+ }
+}
+
+
+static void doUnassemble(char *tokens[], int n) {
+ Word addr, count;
+ Word psw;
+ int i;
+ Word instr;
+
+ if (n == 1) {
+ addr = cpuGetPC();
+ count = 16;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ count = 16;
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &count)) {
+ printf("illegal count\n");
+ return;
+ }
+ if (count == 0) {
+ return;
+ }
+ } else {
+ help03();
+ return;
+ }
+ addr &= ~0x00000003;
+ psw = cpuGetPSW();
+ for (i = 0; i < count; i++) {
+ instr = mmuReadWord(addr);
+ printf("%08X: %08X %s\n",
+ addr, instr, disasm(instr, addr));
+ if (addr + 4 < addr) {
+ /* wrap-around */
+ break;
+ }
+ addr += 4;
+ }
+}
+
+
+static void doBreak(char *tokens[], int n) {
+ Word addr;
+
+ if (n == 1) {
+ cpuResetBreak();
+ showBreak();
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ addr &= ~0x00000003;
+ cpuSetBreak(addr);
+ showBreak();
+ } else {
+ help04();
+ }
+}
+
+
+static void doContinue(char *tokens[], int n) {
+ Word count, i;
+ Word addr;
+
+ if (n == 1) {
+ count = 1;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &count) || count == 0) {
+ printf("illegal count\n");
+ return;
+ }
+ } else {
+ help05();
+ return;
+ }
+ for (i = 0; i < count; i++) {
+ cpuRun();
+ }
+ addr = cpuGetPC();
+ printf("Break at %08X\n", addr);
+ showPC();
+}
+
+
+static void doStep(char *tokens[], int n) {
+ Word count, i;
+
+ if (n == 1) {
+ count = 1;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &count) || count == 0) {
+ printf("illegal count\n");
+ return;
+ }
+ } else {
+ help06();
+ return;
+ }
+ for (i = 0; i < count; i++) {
+ cpuStep();
+ }
+ showPC();
+}
+
+
+static void doPC(char *tokens[], int n) {
+ Word addr;
+
+ if (n == 1) {
+ showPC();
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ addr &= ~0x00000003;
+ cpuSetPC(addr);
+ showPC();
+ } else {
+ help07();
+ }
+}
+
+
+static void explainPSW(Word data) {
+ int i;
+
+ printf("interrupt vector : %s (%s)\n",
+ data & PSW_V ? "on " : "off",
+ data & PSW_V ? "RAM" : "ROM");
+ printf("current user mode : %s (%s)\n",
+ data & PSW_UM ? "on " : "off",
+ data & PSW_UM ? "user" : "kernel");
+ printf("previous user mode : %s (%s)\n",
+ data & PSW_PUM ? "on " : "off",
+ data & PSW_PUM ? "user" : "kernel");
+ printf("old user mode : %s (%s)\n",
+ data & PSW_OUM ? "on " : "off",
+ data & PSW_OUM ? "user" : "kernel");
+ printf("current interrupt enable : %s (%s)\n",
+ data & PSW_IE ? "on " : "off",
+ data & PSW_IE ? "enabled" : "disabled");
+ printf("previous interrupt enable : %s (%s)\n",
+ data & PSW_PIE ? "on " : "off",
+ data & PSW_PIE ? "enabled" : "disabled");
+ printf("old interrupt enable : %s (%s)\n",
+ data & PSW_OIE ? "on " : "off",
+ data & PSW_OIE ? "enabled" : "disabled");
+ printf("last interrupt acknowledged : %02X (%s)\n",
+ (data & PSW_PRIO_MASK) >> 16,
+ exceptionToString((data & PSW_PRIO_MASK) >> 16));
+ for (i = 15; i >= 0; i--) {
+ printf("%-35s: %s (%s)\n",
+ exceptionToString(i),
+ data & (1 << i) ? "on " : "off",
+ data & (1 << i) ? "enabled" : "disabled");
+ }
+}
+
+
+static void doPSW(char *tokens[], int n) {
+ Word data;
+
+ if (n == 1) {
+ data = cpuGetPSW();
+ showPSW();
+ explainPSW(data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &data)) {
+ printf("illegal data\n");
+ return;
+ }
+ data &= 0x0FFFFFFF;
+ cpuSetPSW(data);
+ showPSW();
+ explainPSW(data);
+ } else {
+ help08();
+ }
+}
+
+
+static void doRegister(char *tokens[], int n) {
+ int i, j;
+ int reg;
+ Word data;
+
+ if (n == 1) {
+ for (i = 0; i < 8; i++) {
+ for (j = 0; j < 4; j++) {
+ reg = 8 * j + i;
+ data = cpuGetReg(reg);
+ printf("$%-2d %08X ", reg, data);
+ }
+ printf("\n");
+ }
+ showPSW();
+ showBreak();
+ showPC();
+ } else if (n == 2) {
+ if (!getDecNumber(tokens[1], ®) || reg < 0 || reg >= 32) {
+ printf("illegal register number\n");
+ return;
+ }
+ data = cpuGetReg(reg);
+ printf("$%-2d %08X\n", reg, data);
+ } else if (n == 3) {
+ if (!getDecNumber(tokens[1], ®) || reg < 0 || reg >= 32) {
+ printf("illegal register number\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &data)) {
+ printf("illegal data\n");
+ return;
+ }
+ cpuSetReg(reg, data);
+ } else {
+ help09();
+ }
+}
+
+
+static void doDump(char *tokens[], int n) {
+ Word addr, count;
+ Word psw;
+ Word lo, hi, curr;
+ int lines, i, j;
+ Word tmp;
+ Byte c;
+
+ if (n == 1) {
+ addr = cpuGetPC();
+ count = 16 * 16;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ count = 16 * 16;
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &count)) {
+ printf("illegal count\n");
+ return;
+ }
+ if (count == 0) {
+ return;
+ }
+ } else {
+ help10();
+ return;
+ }
+ psw = cpuGetPSW();
+ lo = addr & ~0x0000000F;
+ hi = addr + count - 1;
+ if (hi < lo) {
+ /* wrap-around */
+ hi = 0xFFFFFFFF;
+ }
+ lines = (hi - lo + 16) >> 4;
+ curr = lo;
+ for (i = 0; i < lines; i++) {
+ printf("%08X: ", curr);
+ for (j = 0; j < 16; j++) {
+ tmp = curr + j;
+ if (tmp < addr || tmp > hi) {
+ printf(" ");
+ } else {
+ c = mmuReadByte(tmp);
+ printf("%02X", c);
+ }
+ printf(" ");
+ }
+ printf(" ");
+ for (j = 0; j < 16; j++) {
+ tmp = curr + j;
+ if (tmp < addr || tmp > hi) {
+ printf(" ");
+ } else {
+ c = mmuReadByte(tmp);
+ if (c >= 32 && c <= 126) {
+ printf("%c", c);
+ } else {
+ printf(".");
+ }
+ }
+ }
+ printf("\n");
+ curr += 16;
+ }
+}
+
+
+static void doMemoryWord(char *tokens[], int n) {
+ Word psw;
+ Word addr;
+ Word data;
+ Word tmpData;
+
+ psw = cpuGetPSW();
+ if (n == 1) {
+ addr = cpuGetPC();
+ data = mmuReadWord(addr);
+ printf("%08X: %08X\n", addr, data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ data = mmuReadWord(addr);
+ printf("%08X: %08X\n", addr, data);
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &tmpData)) {
+ printf("illegal data\n");
+ return;
+ }
+ data = tmpData;
+ mmuWriteWord(addr, data);
+ } else {
+ help11();
+ }
+}
+
+
+static void doMemoryHalf(char *tokens[], int n) {
+ Word psw;
+ Word addr;
+ Half data;
+ Word tmpData;
+
+ psw = cpuGetPSW();
+ if (n == 1) {
+ addr = cpuGetPC();
+ data = mmuReadHalf(addr);
+ printf("%08X: %04X\n", addr, data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ data = mmuReadHalf(addr);
+ printf("%08X: %04X\n", addr, data);
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &tmpData)) {
+ printf("illegal data\n");
+ return;
+ }
+ data = (Half) tmpData;
+ mmuWriteHalf(addr, data);
+ } else {
+ help12();
+ }
+}
+
+
+static void doMemoryByte(char *tokens[], int n) {
+ Word psw;
+ Word addr;
+ Byte data;
+ Word tmpData;
+
+ psw = cpuGetPSW();
+ if (n == 1) {
+ addr = cpuGetPC();
+ data = mmuReadByte(addr);
+ printf("%08X: %02X\n", addr, data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ data = mmuReadByte(addr);
+ printf("%08X: %02X\n", addr, data);
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &tmpData)) {
+ printf("illegal data\n");
+ return;
+ }
+ data = (Byte) tmpData;
+ mmuWriteByte(addr, data);
+ } else {
+ help13();
+ }
+}
+
+
+static void doTLB(char *tokens[], int n) {
+ int index;
+ TLB_Entry tlbEntry;
+ Word data;
+
+ if (n == 1) {
+ for (index = 0; index < TLB_SIZE; index++) {
+ tlbEntry = mmuGetTLB(index);
+ printf("TLB[%02d] page %08X frame %08X %c %c\n",
+ index, tlbEntry.page, tlbEntry.frame,
+ tlbEntry.write ? 'w' : '-',
+ tlbEntry.valid ? 'v' : '-');
+ }
+ printf("Index(1) %08X\n", mmuGetIndex());
+ printf("EntryHi(2) %08X\n", mmuGetEntryHi());
+ printf("EntryLo(3) %08X\n", mmuGetEntryLo());
+ } else if (n == 2) {
+ if (!getDecNumber(tokens[1], &index) || index < 0 || index >= TLB_SIZE) {
+ printf("illegal TLB index\n");
+ return;
+ }
+ tlbEntry = mmuGetTLB(index);
+ printf("TLB[%02d] page %08X frame %08X %c %c\n",
+ index, tlbEntry.page, tlbEntry.frame,
+ tlbEntry.write ? 'w' : '-',
+ tlbEntry.valid ? 'v' : '-');
+ } else if (n == 3) {
+ help14();
+ } else if (n == 4) {
+ if (!getDecNumber(tokens[1], &index) || index < 0 || index >= TLB_SIZE) {
+ printf("illegal TLB index\n");
+ return;
+ }
+ if (!getHexNumber(tokens[3], &data)) {
+ printf("illegal data\n");
+ return;
+ }
+ tlbEntry = mmuGetTLB(index);
+ if (strcmp(tokens[2], "p") == 0) {
+ tlbEntry.page = data & PAGE_MASK;
+ } else
+ if (strcmp(tokens[2], "f") == 0) {
+ tlbEntry.frame = data & PAGE_MASK;
+ tlbEntry.write = data & TLB_WRITE ? true : false;
+ tlbEntry.valid = data & TLB_VALID ? true : false;
+ } else {
+ printf("TLB selector is not one of 'p' or 'f'\n");
+ return;
+ }
+ mmuSetTLB(index, tlbEntry);
+ printf("TLB[%02d] page %08X frame %08X %c %c\n",
+ index, tlbEntry.page, tlbEntry.frame,
+ tlbEntry.write ? 'w' : '-',
+ tlbEntry.valid ? 'v' : '-');
+ } else {
+ help14();
+ }
+}
+
+
+static void doLoad(char *tokens[], int n) {
+ int serno;
+
+ if (n == 2) {
+ if (!getDecNumber(tokens[1], &serno) || serno < 0 || serno > 1) {
+ printf("illegal serial line number\n");
+ return;
+ }
+ load(serno);
+ } else {
+ help15();
+ }
+}
+
+
+static void doBoot(char *tokens[], int n) {
+ int dskno;
+
+ if (n == 2) {
+ if (!getDecNumber(tokens[1], &dskno) || dskno < 0 || dskno > 1) {
+ printf("illegal disk number\n");
+ return;
+ }
+ boot(dskno);
+ } else {
+ help16();
+ }
+}
+
+
+Command commands[] = {
+ { "help", help00, doHelp },
+ { "+", help01, doArith },
+ { "a", help02, doAssemble },
+ { "u", help03, doUnassemble },
+ { "b", help04, doBreak },
+ { "c", help05, doContinue },
+ { "s", help06, doStep },
+ { "#", help07, doPC },
+ { "p", help08, doPSW },
+ { "r", help09, doRegister },
+ { "d", help10, doDump },
+ { "mw", help11, doMemoryWord },
+ { "mh", help12, doMemoryHalf },
+ { "mb", help13, doMemoryByte },
+ { "t", help14, doTLB },
+ { "load", help15, doLoad },
+ { "boot", help16, doBoot },
+};
+
+int numCommands = sizeof(commands) / sizeof(commands[0]);
+
+
+static void doCommand(char *line) {
+ char *tokens[MAX_TOKENS];
+ int n;
+ char *p;
+ int i;
+
+ n = 0;
+ p = strtok(line, " \t\n");
+ while (p != NULL) {
+ if (n == MAX_TOKENS) {
+ printf("too many tokens on line\n");
+ return;
+ }
+ tokens[n++] = p;
+ p = strtok(NULL, " \t\n");
+ }
+ if (n == 0) {
+ return;
+ }
+ for (i = 0; i < numCommands; i++) {
+ if (strcmp(commands[i].name, tokens[0]) == 0) {
+ (*commands[i].cmdProc)(tokens, n);
+ return;
+ }
+ }
+ help();
+}
+
+
+static char *article(char firstLetterOfNoun) {
+ switch (firstLetterOfNoun) {
+ case 'a':
+ case 'e':
+ case 'i':
+ case 'o':
+ case 'u':
+ return "An";
+ default:
+ return "A";
+ }
+}
+
+
+static void interactiveException(int exception) {
+ char *what;
+
+ what = exceptionToString(exception);
+ printf("\n");
+ printf("NOTE: %s %s occurred while executing the command.\n",
+ article(*what), what);
+ printf(" This event will not alter the state of the CPU.\n");
+}
+
+
+void execCommand(char *line) {
+ MonitorState commandState;
+
+ if (saveState(&commandState)) {
+ /* initialization */
+ monitorReturn = &commandState;
+ doCommand(line);
+ } else {
+ /* an exception was thrown */
+ interactiveException((userContext.psw & PSW_PRIO_MASK) >> 16);
+ }
+ monitorReturn = NULL;
+}
Index: monitor/monitor-digilent/asm.c
===================================================================
--- monitor/monitor-digilent/asm.c (nonexistent)
+++ monitor/monitor-digilent/asm.c (revision 16)
@@ -0,0 +1,370 @@
+/*
+ * asm.c -- assembler
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "instr.h"
+#include "asm.h"
+
+
+#define MAX_TOKENS 10
+
+
+static char *msgs[] = {
+ /* 0 */ "too many tokens on line",
+ /* 1 */ "empty line",
+ /* 2 */ "unknown instruction name",
+ /* 3 */ "unknown instruction format",
+ /* 4 */ "excess tokens on line",
+ /* 5 */ "too few operands",
+ /* 6 */ "illegal register",
+ /* 7 */ "illegal immediate value",
+ /* 8 */ "immediate value out of range",
+ /* 9 */ "target is not aligned",
+ /* 10 */ "target cannot be reached"
+};
+
+
+static Bool asmReg(char *token, int *reg) {
+ char *end;
+
+ if (*token != '$') {
+ return false;
+ }
+ *reg = strtoul(token + 1, &end, 10);
+ if (*end != '\0') {
+ return false;
+ }
+ if (*reg < 0 || *reg >= 32) {
+ return false;
+ }
+ return true;
+}
+
+
+static Bool asmNum(char *token, unsigned int *val) {
+ char *end;
+
+ *val = strtoul(token, &end, 16);
+ return *end == '\0';
+}
+
+
+char *asmInstr(char *line, Word addr, Word *instrPtr) {
+ char *tokens[MAX_TOKENS];
+ int n;
+ char *p;
+ Instr *instr;
+ Word result;
+ int r1, r2, r3;
+ unsigned int uimm;
+ signed int simm;
+
+ /* separate tokens */
+ n = 0;
+ p = strtok(line, " \t\n,");
+ while (p != NULL) {
+ if (n == MAX_TOKENS) {
+ return msgs[0];
+ }
+ tokens[n++] = p;
+ p = strtok(NULL, " \t\n,");
+ }
+ if (n == 0) {
+ return msgs[1];
+ }
+ /* lookup mnemonic */
+ instr = lookupInstr(tokens[0]);
+ if (instr == NULL) {
+ return msgs[2];
+ }
+ /* do processing according to format */
+ switch (instr->format) {
+ case FORMAT_N:
+ /* no operands (but may get a constant operand) */
+ if (n > 2) {
+ return msgs[4];
+ }
+ if (n < 1) {
+ return msgs[5];
+ }
+ if (n == 2) {
+ if (!asmNum(tokens[1], &uimm)) {
+ return msgs[7];
+ }
+ } else {
+ uimm = 0;
+ }
+ result = ((Word) instr->opcode << 26) |
+ (uimm & MASK(26));
+ break;
+ case FORMAT_RH:
+ /* one register and a half operand */
+ if (n > 3) {
+ return msgs[4];
+ }
+ if (n < 3) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[2], &uimm)) {
+ return msgs[7];
+ }
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ break;
+ case FORMAT_RHH:
+ /* one register and a half operand */
+ /* ATTENTION: high-order 16 bits encoded */
+ if (n > 3) {
+ return msgs[4];
+ }
+ if (n < 3) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[2], &uimm)) {
+ return msgs[7];
+ }
+ uimm >>= 16;
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ break;
+ case FORMAT_RRH:
+ /* two registers and a half operand */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[3], &uimm)) {
+ return msgs[7];
+ }
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ break;
+ case FORMAT_RRS:
+ /* two registers and a signed half operand */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[3], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if (simm >= (signed) (1 << 15) ||
+ simm < - (signed) (1 << 15)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (simm & MASK(16));
+ break;
+ case FORMAT_RRR:
+ /* three register operands */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[3], &r3)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r3 << 16) |
+ (r1 << 11);
+ break;
+ case FORMAT_RRX:
+ /* either FORMAT_RRR or FORMAT_RRH */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (*tokens[3] == '$') {
+ /* FORMAT_RRR */
+ if (!asmReg(tokens[3], &r3)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r3 << 16) |
+ (r1 << 11);
+ } else {
+ /* FORMAT_RRH */
+ if (!asmNum(tokens[3], &uimm)) {
+ return msgs[7];
+ }
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = (((Word) instr->opcode + 1) << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ }
+ break;
+ case FORMAT_RRY:
+ /* either FORMAT_RRR or FORMAT_RRS */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (*tokens[3] == '$') {
+ /* FORMAT_RRR */
+ if (!asmReg(tokens[3], &r3)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r3 << 16) |
+ (r1 << 11);
+ } else {
+ /* FORMAT_RRS */
+ if (!asmNum(tokens[3], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if (simm >= (signed) (1 << 15) ||
+ simm < - (signed) (1 << 15)) {
+ return msgs[8];
+ }
+ result = (((Word) instr->opcode + 1) << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (simm & MASK(16));
+ }
+ break;
+ case FORMAT_RRB:
+ /* two registers and a 16 bit signed offset operand */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[3], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if ((simm & 0x00000003) != 0) {
+ return msgs[9];
+ }
+ simm -= addr + 4;
+ simm /= 4;
+ if (simm >= (signed) (1 << 15) ||
+ simm < - (signed) (1 << 15)) {
+ return msgs[10];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 21) |
+ (r2 << 16) |
+ (simm & MASK(16));
+ break;
+ case FORMAT_J:
+ /* no registers and a 26 bit signed offset operand */
+ if (n > 2) {
+ return msgs[4];
+ }
+ if (n < 2) {
+ return msgs[5];
+ }
+ if (!asmNum(tokens[1], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if ((simm & 0x00000003) != 0) {
+ return msgs[9];
+ }
+ simm -= addr + 4;
+ simm /= 4;
+ if (simm >= (signed) (1 << 25) ||
+ simm < - (signed) (1 << 25)) {
+ return msgs[10];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (simm & MASK(26));
+ break;
+ case FORMAT_JR:
+ /* one register operand */
+ if (n > 2) {
+ return msgs[4];
+ }
+ if (n < 2) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 21);
+ break;
+ default:
+ return msgs[3];
+ }
+ /* line successfully assembled */
+ *instrPtr = result;
+ return NULL;
+}
Index: monitor/monitor-digilent/monitor.map
===================================================================
--- monitor/monitor-digilent/monitor.map (nonexistent)
+++ monitor/monitor-digilent/monitor.map (revision 16)
@@ -0,0 +1,105 @@
+_bbss BSS 0x00000000
+_bcode CODE 0x00000000
+_bdata DATA 0x00000000
+_ebss BSS 0x00000B70
+_ecode CODE 0x000072B0
+_edata DATA 0x00001A70
+addHist CODE 0x000053CC
+asmInstr CODE 0x0000280C
+boot CODE 0x0000421C
+cin CODE 0x00000010
+cinchk CODE 0x0000000C
+commands DATA 0x00000028
+cout CODE 0x00000018
+coutchk CODE 0x00000014
+cpuGetBreak CODE 0x000043FC
+cpuGetPC CODE 0x00004354
+cpuGetPSW CODE 0x000043C0
+cpuGetReg CODE 0x0000437C
+cpuResetBreak CODE 0x00004438
+cpuRun CODE 0x00004AA8
+cpuSetBreak CODE 0x00004410
+cpuSetPC CODE 0x00004368
+cpuSetPSW CODE 0x000043D4
+cpuSetReg CODE 0x00004398
+cpuStep CODE 0x000045AC
+cpuTestBreak CODE 0x000043E8
+debugBreak CODE 0x000054AC
+disasm CODE 0x00003820
+dskcap CODE 0x0000002C
+dskio CODE 0x00000030
+dspinit CODE 0x00006BC4
+dspout CODE 0x00006C0C
+dspoutchk CODE 0x00006C04
+exceptionToString CODE 0x0000444C
+execCommand CODE 0x000024B0
+getLine CODE 0x00005064
+getTLB_HI CODE 0x000000E8
+getTLB_LO CODE 0x000000F8
+getchar CODE 0x00005BB4
+initInstrTable CODE 0x0000255C
+instrCodeTbl BSS 0x0000009C
+instrTbl DATA 0x00000F60
+kbdin CODE 0x00006840
+kbdinchk CODE 0x0000682C
+kbdinit CODE 0x00006828
+load CODE 0x00003CB8
+lookupInstr CODE 0x00002680
+main CODE 0x00000320
+mmuGetEntryHi CODE 0x00004EF0
+mmuGetEntryLo CODE 0x00004F18
+mmuGetIndex CODE 0x00004EC8
+mmuGetTLB CODE 0x00004F40
+mmuReadByte CODE 0x00004E98
+mmuReadHalf CODE 0x00004E8C
+mmuReadWord CODE 0x00004E80
+mmuSetEntryHi CODE 0x00004F04
+mmuSetEntryLo CODE 0x00004F2C
+mmuSetIndex CODE 0x00004EDC
+mmuSetTLB CODE 0x00005008
+mmuWriteByte CODE 0x00004EBC
+mmuWriteHalf CODE 0x00004EB0
+mmuWriteWord CODE 0x00004EA4
+monitorReturn BSS 0x00000000
+numCommands DATA 0x000000F4
+printf CODE 0x00006740
+putchar CODE 0x00005BD8
+puts CODE 0x00005C14
+qsort CODE 0x00005B68
+resume CODE 0x000001C8
+saveState CODE 0x00000154
+sctcapctl CODE 0x00006F54
+sctcapser CODE 0x000070C4
+sctioctl CODE 0x00006F8C
+sctioser CODE 0x00007198
+ser0in CODE 0x00006E98
+ser0inchk CODE 0x00006E84
+ser0out CODE 0x00006EC8
+ser0outchk CODE 0x00006EB4
+ser1in CODE 0x00006EFC
+ser1inchk CODE 0x00006EE4
+ser1out CODE 0x00006F34
+ser1outchk CODE 0x00006F1C
+serinit CODE 0x00006E80
+setTLB CODE 0x00000108
+sin CODE 0x00000020
+sinchk CODE 0x0000001C
+sout CODE 0x00000028
+soutchk CODE 0x00000024
+sprintf CODE 0x000067E4
+strcat CODE 0x0000555C
+strchr CODE 0x000055A8
+strcmp CODE 0x000054E8
+strcpy CODE 0x00005520
+strlen CODE 0x000054B0
+strtok CODE 0x000055D8
+strtoul CODE 0x000058AC
+userContext BSS 0x00000004
+vprintf CODE 0x00006700
+vsprintf CODE 0x0000678C
+xltbl1 CODE 0x000069C4
+xltbl2 CODE 0x00006AC4
+
+CODE start 0xE0000000 size 0x000072B0
+DATA start 0xC3FFC000 size 0x00001A70
+BSS start 0xC3FFDA70 size 0x00000B70
Index: monitor/monitor-digilent/command.h
===================================================================
--- monitor/monitor-digilent/command.h (nonexistent)
+++ monitor/monitor-digilent/command.h (revision 16)
@@ -0,0 +1,13 @@
+/*
+ * command.h -- command interpreter
+ */
+
+
+#ifndef _COMMAND_H_
+#define _COMMAND_H_
+
+
+void execCommand(char *line);
+
+
+#endif /* _COMMAND_H_ */
Index: monitor/monitor-digilent/main.c
===================================================================
--- monitor/monitor-digilent/main.c (nonexistent)
+++ monitor/monitor-digilent/main.c (revision 16)
@@ -0,0 +1,27 @@
+/*
+ * main.c -- the main program
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "command.h"
+#include "getline.h"
+#include "instr.h"
+#include "cpu.h"
+
+
+int main(void) {
+ char *line;
+
+ printf("\n\nECO32 Machine Monitor 1.1\n\n");
+ initInstrTable();
+ cpuSetPC(0xC0000000);
+ while (1) {
+ line = getLine("ECO32 > ");
+ addHist(line);
+ execCommand(line);
+ }
+ return 0;
+}
Index: monitor/monitor-digilent/asm.h
===================================================================
--- monitor/monitor-digilent/asm.h (nonexistent)
+++ monitor/monitor-digilent/asm.h (revision 16)
@@ -0,0 +1,13 @@
+/*
+ * asm.h -- assembler
+ */
+
+
+#ifndef _ASM_H_
+#define _ASM_H_
+
+
+char *asmInstr(char *line, Word addr, Word *instrPtr);
+
+
+#endif /* _ASM_H_ */
Index: monitor/monitor-digilent/sctio-ser.s
===================================================================
--- monitor/monitor-digilent/sctio-ser.s (nonexistent)
+++ monitor/monitor-digilent/sctio-ser.s (revision 16)
@@ -0,0 +1,200 @@
+;
+; sctio-ser.s -- disk sector I/O for disk made available by serial interface
+;
+
+;***************************************************************
+
+ .export sctcapser ; determine disk capacity
+ .export sctioser ; do disk I/O
+
+ .import ser1in
+ .import ser1out
+ .import ser1inchk
+ .import puts
+
+ ; constants for communication with disk server
+ .set SYN,0x16 ; to initiate the three-way handshake
+ .set ACK,0x06 ; acknowledgement for handshake
+ .set RESULT_OK,0x00 ; server successfully executed cmd
+ ; everything else means error
+
+ .set WAIT_DELAY,800000 ; count for delay loop
+
+;***************************************************************
+
+ .code
+ .align 4
+
+sctcapser:
+ sub $29,$29,16
+ stw $16,$29,0
+ stw $17,$29,4
+ stw $18,$29,8
+ stw $31,$29,12
+ add $4,$0,trymsg ; say what we are doing
+ jal puts
+ add $18,$0,$0 ; capacity == 0 if disk not present
+ add $16,$0,10 ; 10 tries to get a connection
+handshake1:
+ sub $16,$16,1
+ add $4,$0,SYN
+ jal ser1out ; send SYN
+ add $17,$0,WAIT_DELAY ; wait for ACK
+handshake2:
+ sub $17,$17,1
+ jal ser1inchk
+ bne $2,$0,handshake3
+ bne $17,$0,handshake2
+ add $4,$0,timeoutmsg
+ jal puts
+ bne $16,$0,handshake1
+ add $4,$0,frustratedmsg
+ jal puts
+ j sctcapx
+handshake3:
+ jal ser1in
+ add $8,$0,ACK
+ bne $2,$8,sctcapx
+ ; we got an ACK so we return it
+ add $4,$0,ACK
+ jal ser1out
+
+ ; ask it for its capacity
+ add $4,$0,'c'
+ jal ser1out ; request
+ jal ser1in ; first byte of response
+ bne $2,$0,sctcapx ; exit if error
+
+ ; all is well and the server will give us the capacity
+ add $16,$0,4 ; 4 bytes to read
+sctcap1:
+ sll $18,$18,8
+ jal ser1in
+ or $18,$18,$2 ; most significant byte first
+ sub $16,$16,1
+ bne $16,$0,sctcap1
+
+ ; return value is in $18
+sctcapx:
+ add $2,$0,$18
+ ldw $16,$29,0
+ ldw $17,$29,4
+ ldw $18,$29,8
+ ldw $31,$29,12
+ add $29,$29,16
+ jr $31
+
+ .data
+ .align 4
+
+trymsg:
+ .byte "Trying to connect to disk server..."
+ .byte 0x0A, 0
+
+timeoutmsg:
+ .byte "Request timed out..."
+ .byte 0x0A, 0
+
+frustratedmsg:
+ .byte "Unable to establish connection to disk server."
+ .byte 0x0A, 0
+
+ .code
+ .align 4
+
+sctioser:
+ sub $29,$29,24
+ stw $16,$29,0
+ stw $17,$29,4
+ stw $18,$29,8
+ stw $19,$29,12
+ stw $20,$29,16
+ stw $31,$29,20
+ add $16,$0,$4 ; command
+ add $17,$0,$5 ; start at sector
+ add $8,$0,0xc0000000
+ or $18,$8,$6 ; memory address (logicalized)
+ add $19,$0,$7 ; number of sectors
+
+ ; switch over command
+ add $8,$0,'r'
+ beq $8,$16,sctior ; read
+ add $8,$0,'w'
+ beq $8,$16,sctiow ; write
+ ; unknown command
+ add $2,$0,1 ; value != 0 signifies error
+ j sctiox
+
+ ; read from disk
+sctior:
+sctior1: ; loop over number of sectors
+ beq $19,$0,sctiorsuc ; successful return
+ sub $19,$19,1
+ ; read a sector
+ add $4,$0,'r'
+ jal ser1out
+ ; send sector number
+ add $20,$0,32 ; 4 bytes
+sctior2:
+ sub $20,$20,8
+ slr $4,$17,$20
+ and $4,$4,0xff
+ jal ser1out
+ bne $20,$0,sctior2
+ add $17,$17,1
+ ; get answer
+ jal ser1in
+ bne $2,$0,sctiox ; $2 != 0 so we use it as return code
+ ; read data
+ add $20,$0,512
+sctior3:
+ sub $20,$20,1
+ jal ser1in
+ stb $2,$18,0
+ add $18,$18,1
+ bne $20,$0,sctior3
+ j sctior1
+sctiorsuc:
+ add $2,$0,$0
+ j sctiox
+
+ ; write to disk
+sctiow:
+sctiow1: ; loop over number of sectors
+ beq $19,$0,sctiowsuc ; successful return
+ sub $19,$19,1
+ ; write a sector
+ add $4,$0,'w'
+ jal ser1out
+ ; send sector number
+ add $20,$0,32 ; 4 bytes
+sctiow2:
+ sub $20,$20,8
+ slr $4,$17,$20
+ and $4,$4,0xff
+ jal ser1out
+ bne $20,$0,sctiow2
+ add $17,$17,1
+ ; write data
+ add $20,$0,512
+sctiow3:
+ sub $20,$20,1
+ ldbu $4,$18,0
+ jal ser1out
+ add $18,$18,1
+ bne $20,$0,sctiow3
+ ; get answer
+ jal ser1in
+ bne $2,$0,sctiox
+ j sctiow1
+sctiowsuc:
+ add $2,$0,$0
+sctiox:
+ ldw $16,$29,0
+ ldw $17,$29,4
+ ldw $18,$29,8
+ ldw $19,$29,12
+ ldw $20,$29,16
+ ldw $31,$29,20
+ add $29,$29,24
+ jr $31
Index: monitor/monitor-digilent/stdarg.h
===================================================================
--- monitor/monitor-digilent/stdarg.h (nonexistent)
+++ monitor/monitor-digilent/stdarg.h (revision 16)
@@ -0,0 +1,41 @@
+/*
+ * stdarg.h -- variable argument lists
+ */
+
+
+#ifndef _STDARG_H_
+#define _STDARG_H_
+
+
+typedef char *va_list;
+
+
+static float __va_arg_tmp;
+
+
+#define va_start(list, start) \
+ ((void)((list) = (sizeof(start)<4 ? \
+ (char *)((int *)&(start)+1) : (char *)(&(start)+1))))
+
+#define __va_arg(list, mode, n) \
+ (__typecode(mode)==1 && sizeof(mode)==4 ? \
+ (__va_arg_tmp = *(double *)(&(list += \
+ ((sizeof(double)+n)&~n))[-(int)((sizeof(double)+n)&~n)]), \
+ *(mode *)&__va_arg_tmp) : \
+ *(mode *)(&(list += \
+ ((sizeof(mode)+n)&~n))[-(int)((sizeof(mode)+n)&~n)]))
+
+#define _bigendian_va_arg(list, mode, n) \
+ (sizeof(mode)==1 ? *(mode *)(&(list += 4)[-1]) : \
+ sizeof(mode)==2 ? *(mode *)(&(list += 4)[-2]) : \
+ __va_arg(list, mode, n))
+
+#define va_end(list) ((void)0)
+
+#define va_arg(list, mode) \
+ (sizeof(mode)==8 ? \
+ *(mode *)(&(list = (char*)(((int)list + 15)&~7U))[-8]) : \
+ _bigendian_va_arg(list, mode, 3U))
+
+
+#endif /* _STDARG_H_ */
Index: monitor/monitor-digilent/common.h
===================================================================
--- monitor/monitor-digilent/common.h (nonexistent)
+++ monitor/monitor-digilent/common.h (revision 16)
@@ -0,0 +1,27 @@
+/*
+ * common.h -- common definitions
+ */
+
+
+#ifndef _COMMON_H_
+#define _COMMON_H_
+
+
+#define PAGE_SHIFT 12 /* log2 of page size */
+#define PAGE_SIZE (1 << PAGE_SHIFT) /* page size in bytes */
+#define OFFSET_MASK (PAGE_SIZE - 1) /* mask for offset in page */
+#define PAGE_MASK (~OFFSET_MASK) /* mask for page number */
+
+
+typedef enum { false, true } Bool; /* truth values */
+
+
+typedef unsigned int Word; /* 32 bit quantities */
+typedef unsigned short Half; /* 16 bit quantities */
+typedef unsigned char Byte; /* 8 bit quantities */
+
+
+#define NULL ((void *) 0)
+
+
+#endif /* _COMMON_H_ */
Index: monitor/kbdtbls/Makefile
===================================================================
--- monitor/kbdtbls/Makefile (nonexistent)
+++ monitor/kbdtbls/Makefile (revision 16)
@@ -0,0 +1,18 @@
+#
+# Makefile to construct the keyboard mapping tables
+#
+
+.PHONY: all install clean
+
+all: kbdtbls.s
+
+install: kbdtbls.s
+
+kbdtbls.s: mkkbdtbls
+ ./mkkbdtbls > kbdtbls.s
+
+mkkbdtbls: mkkbdtbls.c
+ gcc -m32 -g -Wall -o mkkbdtbls mkkbdtbls.c
+
+clean:
+ rm -f *~ mkkbdtbls kbdtbls.s
Index: monitor/kbdtbls/mkkbdtbls.c
===================================================================
--- monitor/kbdtbls/mkkbdtbls.c (nonexistent)
+++ monitor/kbdtbls/mkkbdtbls.c (revision 16)
@@ -0,0 +1,171 @@
+/*
+ * mkkbdtbls.c -- construct keyboard translation tables
+ */
+
+
+#include
+#include
+#include
+
+
+typedef struct {
+ unsigned char ascii;
+ unsigned char key;
+} Entry;
+
+
+Entry tbl1[] = {
+ { 0x1B, 0x76 },
+ { '1', 0x16 },
+ { '2', 0x1E },
+ { '3', 0x26 },
+ { '4', 0x25 },
+ { '5', 0x2E },
+ { '6', 0x36 },
+ { '7', 0x3D },
+ { '8', 0x3E },
+ { '9', 0x46 },
+ { '0', 0x45 },
+ { '^', 0x0E },
+ { 0x08, 0x66 },
+ { 0x09, 0x0D },
+ { 'q', 0x15 },
+ { 'w', 0x1D },
+ { 'e', 0x24 },
+ { 'r', 0x2D },
+ { 't', 0x2C },
+ { 'z', 0x35 },
+ { 'u', 0x3C },
+ { 'i', 0x43 },
+ { 'o', 0x44 },
+ { 'p', 0x4D },
+ { '\r', 0x5A },
+ { ' ', 0x29 },
+ { 'a', 0x1C },
+ { 's', 0x1B },
+ { 'd', 0x23 },
+ { 'f', 0x2B },
+ { 'g', 0x34 },
+ { 'h', 0x33 },
+ { 'j', 0x3B },
+ { 'k', 0x42 },
+ { 'l', 0x4B },
+ { 'y', 0x1A },
+ { 'x', 0x22 },
+ { 'c', 0x21 },
+ { 'v', 0x2A },
+ { 'b', 0x32 },
+ { 'n', 0x31 },
+ { 'm', 0x3A },
+ { ',', 0x41 },
+ { '.', 0x49 },
+ { '-', 0x4A },
+ { '+', 0x5B },
+ { '#', 0x5D },
+ { '<', 0x61 },
+};
+
+
+Entry tbl2[] = {
+ { 0x1B, 0x76 },
+ { '!', 0x16 },
+ { '"', 0x1E },
+ { '3', 0x26 },
+ { '$', 0x25 },
+ { '%', 0x2E },
+ { '&', 0x36 },
+ { '/', 0x3D },
+ { '(', 0x3E },
+ { ')', 0x46 },
+ { '=', 0x45 },
+ { '^', 0x0E },
+ { 0x08, 0x66 },
+ { 0x09, 0x0D },
+ { 'Q', 0x15 },
+ { 'W', 0x1D },
+ { 'E', 0x24 },
+ { 'R', 0x2D },
+ { 'T', 0x2C },
+ { 'Z', 0x35 },
+ { 'U', 0x3C },
+ { 'I', 0x43 },
+ { 'O', 0x44 },
+ { 'P', 0x4D },
+ { '\r', 0x5A },
+ { ' ', 0x29 },
+ { 'A', 0x1C },
+ { 'S', 0x1B },
+ { 'D', 0x23 },
+ { 'F', 0x2B },
+ { 'G', 0x34 },
+ { 'H', 0x33 },
+ { 'J', 0x3B },
+ { 'K', 0x42 },
+ { 'L', 0x4B },
+ { 'Y', 0x1A },
+ { 'X', 0x22 },
+ { 'C', 0x21 },
+ { 'V', 0x2A },
+ { 'B', 0x32 },
+ { 'N', 0x31 },
+ { 'M', 0x3A },
+ { ';', 0x41 },
+ { ':', 0x49 },
+ { '_', 0x4A },
+ { '*', 0x5B },
+ { '\'', 0x5D },
+ { '>', 0x61 },
+};
+
+
+int main(void) {
+ unsigned char codes[256];
+ int i, j;
+
+ for (i = 0; i < 256; i++) {
+ codes[i] = '\0';
+ }
+ for (i = 0; i < sizeof(tbl1)/sizeof(tbl1[0]); i++) {
+ codes[tbl1[i].key] = tbl1[i].ascii;
+ }
+ printf(";\n");
+ printf("; keyboard code tables\n");
+ printf(";\n");
+ printf("\n");
+ printf("\t.export\txltbl1\n");
+ printf("\t.export\txltbl2\n");
+ printf("\n");
+ printf("\t.code\n");
+ printf("\t.align\t4\n");
+ printf("\n");
+ printf("xltbl1:\n");
+ for (i = 0; i < 32; i++) {
+ printf("\t.byte\t");
+ for (j = 0; j < 8; j++) {
+ printf("0x%02X", codes[i * 8 + j]);
+ if (j < 7) {
+ printf(", ");
+ }
+ }
+ printf("\n");
+ }
+ printf("\n");
+ for (i = 0; i < 256; i++) {
+ codes[i] = '\0';
+ }
+ for (i = 0; i < sizeof(tbl2)/sizeof(tbl2[0]); i++) {
+ codes[tbl2[i].key] = tbl2[i].ascii;
+ }
+ printf("xltbl2:\n");
+ for (i = 0; i < 32; i++) {
+ printf("\t.byte\t");
+ for (j = 0; j < 8; j++) {
+ printf("0x%02X", codes[i * 8 + j]);
+ if (j < 7) {
+ printf(", ");
+ }
+ }
+ printf("\n");
+ }
+ return 0;
+}
Index: monitor/monitor/mmu.c
===================================================================
--- monitor/monitor/mmu.c (nonexistent)
+++ monitor/monitor/mmu.c (revision 16)
@@ -0,0 +1,104 @@
+/*
+ * mmu.c -- memory and TLB access
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "mmu.h"
+#include "start.h"
+
+
+static Word tlbIndex;
+static Word tlbEntryHi;
+static Word tlbEntryLo;
+
+
+Word mmuReadWord(Word vAddr) {
+ return *(Word *)vAddr;
+}
+
+
+Half mmuReadHalf(Word vAddr) {
+ return *(Half *)vAddr;
+}
+
+
+Byte mmuReadByte(Word vAddr) {
+ return *(Byte *)vAddr;
+}
+
+
+void mmuWriteWord(Word vAddr, Word data) {
+ *(Word *)vAddr = data;
+}
+
+
+void mmuWriteHalf(Word vAddr, Half data) {
+ *(Half *)vAddr = data;
+}
+
+
+void mmuWriteByte(Word vAddr, Byte data) {
+ *(Byte *)vAddr = data;
+}
+
+
+Word mmuGetIndex(void) {
+ return tlbIndex;
+}
+
+
+void mmuSetIndex(Word value) {
+ tlbIndex = value;
+}
+
+
+Word mmuGetEntryHi(void) {
+ return tlbEntryHi;
+}
+
+
+void mmuSetEntryHi(Word value) {
+ tlbEntryHi = value;
+}
+
+
+Word mmuGetEntryLo(void) {
+ return tlbEntryLo;
+}
+
+
+void mmuSetEntryLo(Word value) {
+ tlbEntryLo = value;
+}
+
+
+TLB_Entry mmuGetTLB(int index) {
+ Word hi;
+ Word lo;
+ TLB_Entry result;
+
+ hi = getTLB_HI(index);
+ lo = getTLB_LO(index);
+ result.page = hi & PAGE_MASK;
+ result.frame = lo & PAGE_MASK;
+ result.write = (lo & TLB_WRITE) ? true : false;
+ result.valid = (lo & TLB_VALID) ? true : false;
+ return result;
+}
+
+
+void mmuSetTLB(int index, TLB_Entry tlbEntry) {
+ Word flags;
+
+ flags = 0;
+ if (tlbEntry.write) {
+ flags |= TLB_WRITE;
+ }
+ if (tlbEntry.valid) {
+ flags |= TLB_VALID;
+ }
+ setTLB(index, tlbEntry.page, tlbEntry.frame | flags);
+}
Index: monitor/monitor/instr.c
===================================================================
--- monitor/monitor/instr.c (nonexistent)
+++ monitor/monitor/instr.c (revision 16)
@@ -0,0 +1,115 @@
+/*
+ * instr.c -- instruction encoding
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "instr.h"
+
+
+/*
+ * This is the ECO32 machine instruction set.
+ * The table below needs no particular order
+ * and may have gaps in the instruction encoding.
+ */
+Instr instrTbl[] = {
+ { "add", FORMAT_RRY, OP_ADD },
+ { "sub", FORMAT_RRY, OP_SUB },
+ { "mul", FORMAT_RRY, OP_MUL },
+ { "mulu", FORMAT_RRX, OP_MULU },
+ { "div", FORMAT_RRY, OP_DIV },
+ { "divu", FORMAT_RRX, OP_DIVU },
+ { "rem", FORMAT_RRY, OP_REM },
+ { "remu", FORMAT_RRX, OP_REMU },
+ { "and", FORMAT_RRX, OP_AND },
+ { "or", FORMAT_RRX, OP_OR },
+ { "xor", FORMAT_RRX, OP_XOR },
+ { "xnor", FORMAT_RRX, OP_XNOR },
+ { "sll", FORMAT_RRX, OP_SLL },
+ { "slr", FORMAT_RRX, OP_SLR },
+ { "sar", FORMAT_RRX, OP_SAR },
+ { "ldhi", FORMAT_RHH, OP_LDHI },
+ { "beq", FORMAT_RRB, OP_BEQ },
+ { "bne", FORMAT_RRB, OP_BNE },
+ { "ble", FORMAT_RRB, OP_BLE },
+ { "bleu", FORMAT_RRB, OP_BLEU },
+ { "blt", FORMAT_RRB, OP_BLT },
+ { "bltu", FORMAT_RRB, OP_BLTU },
+ { "bge", FORMAT_RRB, OP_BGE },
+ { "bgeu", FORMAT_RRB, OP_BGEU },
+ { "bgt", FORMAT_RRB, OP_BGT },
+ { "bgtu", FORMAT_RRB, OP_BGTU },
+ { "j", FORMAT_J, OP_J },
+ { "jr", FORMAT_JR, OP_JR },
+ { "jal", FORMAT_J, OP_JAL },
+ { "jalr", FORMAT_JR, OP_JALR },
+ { "trap", FORMAT_N, OP_TRAP },
+ { "rfx", FORMAT_N, OP_RFX },
+ { "ldw", FORMAT_RRS, OP_LDW },
+ { "ldh", FORMAT_RRS, OP_LDH },
+ { "ldhu", FORMAT_RRS, OP_LDHU },
+ { "ldb", FORMAT_RRS, OP_LDB },
+ { "ldbu", FORMAT_RRS, OP_LDBU },
+ { "stw", FORMAT_RRS, OP_STW },
+ { "sth", FORMAT_RRS, OP_STH },
+ { "stb", FORMAT_RRS, OP_STB },
+ { "mvfs", FORMAT_RH, OP_MVFS },
+ { "mvts", FORMAT_RH, OP_MVTS },
+ { "tbs", FORMAT_N, OP_TBS },
+ { "tbwr", FORMAT_N, OP_TBWR },
+ { "tbri", FORMAT_N, OP_TBRI },
+ { "tbwi", FORMAT_N, OP_TBWI }
+};
+
+
+Instr *instrCodeTbl[64];
+
+
+static int instrCompare(const void *instr1, const void *instr2) {
+ return strcmp(((Instr *) instr1)->name, ((Instr *) instr2)->name);
+}
+
+
+void initInstrTable(void) {
+ int i;
+
+ /* first sort instruction table alphabetically */
+ qsort(instrTbl, sizeof(instrTbl)/sizeof(instrTbl[0]),
+ sizeof(instrTbl[0]), instrCompare);
+ /* then initialize instruction code table */
+ for (i = 0; i < 64; i++) {
+ instrCodeTbl[i] = NULL;
+ }
+ for (i = 0; i < sizeof(instrTbl)/sizeof(instrTbl[0]); i++) {
+ instrCodeTbl[instrTbl[i].opcode] = &instrTbl[i];
+ if (instrTbl[i].format == FORMAT_RRX ||
+ instrTbl[i].format == FORMAT_RRY) {
+ /* enter the immediate variant of this instruction also */
+ instrCodeTbl[instrTbl[i].opcode + 1] = &instrTbl[i];
+ }
+ }
+}
+
+
+Instr *lookupInstr(char *name) {
+ int lo, hi, tst;
+ int res;
+
+ lo = 0;
+ hi = sizeof(instrTbl) / sizeof(instrTbl[0]) - 1;
+ while (lo <= hi) {
+ tst = (lo + hi) / 2;
+ res = strcmp(instrTbl[tst].name, name);
+ if (res == 0) {
+ return &instrTbl[tst];
+ }
+ if (res < 0) {
+ lo = tst + 1;
+ } else {
+ hi = tst - 1;
+ }
+ }
+ return NULL;
+}
Index: monitor/monitor/serial.s
===================================================================
--- monitor/monitor/serial.s (nonexistent)
+++ monitor/monitor/serial.s (revision 16)
@@ -0,0 +1,98 @@
+;
+; serial.s -- the serial line interface
+;
+
+;***************************************************************
+
+ .set ser0base,0xF0300000 ; serial line 0 base address
+ .set ser1base,0xF0300010 ; serial line 1 base address
+
+ .export serinit ; initialize serial interface
+
+ .export ser0inchk ; line 0 input check
+ .export ser0in ; line 0 input
+ .export ser0outchk ; line 0 output check
+ .export ser0out ; line 0 output
+
+ .export ser1inchk ; line 1 input check
+ .export ser1in ; line 1 input
+ .export ser1outchk ; line 1 output check
+ .export ser1out ; line 1 output
+
+;***************************************************************
+
+ .code
+ .align 4
+
+serinit:
+ jr $31
+
+;***************************************************************
+
+ .code
+ .align 4
+
+ser0inchk:
+ add $8,$0,ser0base
+ ldw $2,$8,0
+ and $2,$2,1
+ jr $31
+
+ser0in:
+ add $8,$0,ser0base
+ser0in1:
+ ldw $9,$8,0
+ and $9,$9,1
+ beq $9,$0,ser0in1
+ ldw $2,$8,4
+ jr $31
+
+ser0outchk:
+ add $8,$0,ser0base
+ ldw $2,$8,8
+ and $2,$2,1
+ jr $31
+
+ser0out:
+ add $8,$0,ser0base
+ser0out1:
+ ldw $9,$8,8
+ and $9,$9,1
+ beq $9,$0,ser0out1
+ stw $4,$8,12
+ jr $31
+
+;***************************************************************
+
+ .code
+ .align 4
+
+ser1inchk:
+ add $8,$0,ser1base
+ ldw $2,$8,0
+ and $2,$2,1
+ jr $31
+
+ser1in:
+ add $8,$0,ser1base
+ser1in1:
+ ldw $9,$8,0
+ and $9,$9,1
+ beq $9,$0,ser1in1
+ ldw $2,$8,4
+ jr $31
+
+ser1outchk:
+ add $8,$0,ser1base
+ ldw $2,$8,8
+ and $2,$2,1
+ jr $31
+
+ser1out:
+ add $8,$0,ser1base
+ser1out1:
+ ldw $9,$8,8
+ and $9,$9,1
+ beq $9,$0,ser1out1
+ stw $4,$8,12
+ jr $31
Index: monitor/monitor/start.h
===================================================================
--- monitor/monitor/start.h (nonexistent)
+++ monitor/monitor/start.h (revision 16)
@@ -0,0 +1,57 @@
+/*
+ * start.h -- ECO32 ROM monitor startup and support routines
+ */
+
+
+#ifndef _START_H_
+#define _START_H_
+
+
+typedef struct {
+ Word reg[32]; /* general purpose registers */
+ Word psw; /* PSW */
+ Word tlbIndex; /* TLB index register */
+ Word tlbHi; /* TLB EntryHi register */
+ Word tlbLo; /* TLB EntryLo register */
+} UserContext;
+
+typedef struct {
+ Word r31; /* return address */
+ Word r29; /* stack pointer */
+ Word r16; /* local variable */
+ Word r17; /* local variable */
+ Word r18; /* local variable */
+ Word r19; /* local variable */
+ Word r20; /* local variable */
+ Word r21; /* local variable */
+ Word r22; /* local variable */
+ Word r23; /* local variable */
+} MonitorState;
+
+
+int cinchk(void);
+int cin(void);
+int coutchk(void);
+void cout(char c);
+
+int sinchk(void);
+int sin(void);
+int soutchk(void);
+void sout(char c);
+
+int dskcap(int dskno);
+int dskio(int dskno, char cmd, int sct, Word addr, int nscts);
+
+Word getTLB_HI(int index);
+Word getTLB_LO(int index);
+void setTLB(int index, Word entryHi, Word entryLo);
+
+Bool saveState(MonitorState *msp);
+
+extern MonitorState *monitorReturn;
+extern UserContext userContext;
+
+void resume(void);
+
+
+#endif /* _START_H_ */
Index: monitor/monitor/boot.c
===================================================================
--- monitor/monitor/boot.c (nonexistent)
+++ monitor/monitor/boot.c (revision 16)
@@ -0,0 +1,47 @@
+/*
+ * boot.c -- bootstrap from disk
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "boot.h"
+#include "cpu.h"
+#include "mmu.h"
+#include "start.h"
+
+
+void boot(int dskno) {
+ Word capacity;
+ Byte sig1, sig2;
+
+ capacity = dskcap(dskno);
+ if (capacity == 0) {
+ printf("Disk not found!\n");
+ return;
+ }
+ printf("Disk with 0x%08X sectors found, booting...\n", capacity);
+ if (dskio(dskno, 'r', 0, PHYS_BOOT, 1) != 0) {
+ printf("Disk error!\n");
+ return;
+ }
+ sig1 = mmuReadByte(VIRT_BOOT + 512 - 2);
+ sig2 = mmuReadByte(VIRT_BOOT + 512 - 1);
+ if (sig1 != 0x55 || sig2 != 0xAA) {
+ printf("MBR signature missing!\n");
+ return;
+ }
+ /*
+ * Boot convention:
+ * $16 disk number of boot disk
+ * $17 start sector number of disk or partition to boot
+ * $18 total number of sectors of disk or partition to boot
+ */
+ cpuSetReg(16, dskno);
+ cpuSetReg(17, 0);
+ cpuSetReg(18, capacity);
+ cpuSetReg(29, TOS_BOOT);
+ cpuSetPC(VIRT_BOOT);
+ cpuRun();
+}
Index: monitor/monitor/mmu.h
===================================================================
--- monitor/monitor/mmu.h (nonexistent)
+++ monitor/monitor/mmu.h (revision 16)
@@ -0,0 +1,45 @@
+/*
+ * mmu.h -- memory and TLB access
+ */
+
+
+#ifndef _MMU_H_
+#define _MMU_H_
+
+
+#define TLB_SHFT 5 /* log2 of number of TLB entries */
+#define TLB_SIZE (1 << TLB_SHFT) /* total number of TLB entries */
+#define TLB_MASK (TLB_SIZE - 1) /* mask for number of TLB entries */
+#define TLB_FIXED 4 /* number of fixed TLB entries */
+
+#define TLB_WRITE (1 << 1) /* write bit in EntryLo */
+#define TLB_VALID (1 << 0) /* valid bit in EntryLo */
+
+
+typedef struct {
+ Word page; /* 20 high-order bits of virtual address */
+ Word frame; /* 20 high-order bits of physical address */
+ Bool write; /* must be true to allow writing to the page */
+ Bool valid; /* must be true for the entry to be valid */
+} TLB_Entry;
+
+
+Word mmuReadWord(Word vAddr);
+Half mmuReadHalf(Word vAddr);
+Byte mmuReadByte(Word vAddr);
+void mmuWriteWord(Word vAddr, Word data);
+void mmuWriteHalf(Word vAddr, Half data);
+void mmuWriteByte(Word vAddr, Byte data);
+
+Word mmuGetIndex(void);
+void mmuSetIndex(Word value);
+Word mmuGetEntryHi(void);
+void mmuSetEntryHi(Word value);
+Word mmuGetEntryLo(void);
+void mmuSetEntryLo(Word Value);
+
+TLB_Entry mmuGetTLB(int index);
+void mmuSetTLB(int index, TLB_Entry tlbEntry);
+
+
+#endif /* _MMU_H_ */
Index: monitor/monitor/instr.h
===================================================================
--- monitor/monitor/instr.h (nonexistent)
+++ monitor/monitor/instr.h (revision 16)
@@ -0,0 +1,125 @@
+/*
+ * instr.h -- instruction encoding
+ */
+
+
+#ifndef _INSTR_H_
+#define _INSTR_H_
+
+
+#define FORMAT_N 0 /* no operands */
+#define FORMAT_RH 1 /* one register and a half operand */
+#define FORMAT_RHH 2 /* one register and a half operand */
+ /* ATTENTION: high-order 16 bits encoded */
+#define FORMAT_RRH 3 /* two registers and a half operand */
+#define FORMAT_RRS 4 /* two registers and a signed half operand */
+#define FORMAT_RRR 5 /* three register operands */
+#define FORMAT_RRX 6 /* either FORMAT_RRR or FORMAT_RRH */
+#define FORMAT_RRY 7 /* either FORMAT_RRR or FORMAT_RRS */
+#define FORMAT_RRB 8 /* two registers and a 16 bit signed
+ offset operand */
+#define FORMAT_J 9 /* no registers and a 26 bit signed
+ offset operand */
+#define FORMAT_JR 10 /* one register operand */
+
+
+#define MASK(n) ((((Word) 1) << n) - 1)
+#define SIGN(n) (((Word) 1) << (n - 1))
+#define ZEXT16(x) (((Word) (x)) & MASK(16))
+#define SEXT16(x) (((Word) (x)) & SIGN(16) ? \
+ (((Word) (x)) | ~MASK(16)) : \
+ (((Word) (x)) & MASK(16)))
+#define SEXT26(x) (((Word) (x)) & SIGN(26) ? \
+ (((Word) (x)) | ~MASK(26)) : \
+ (((Word) (x)) & MASK(26)))
+
+
+#define OP_ADD 0x00
+#define OP_ADDI 0x01
+#define OP_SUB 0x02
+#define OP_SUBI 0x03
+
+#define OP_MUL 0x04
+#define OP_MULI 0x05
+#define OP_MULU 0x06
+#define OP_MULUI 0x07
+#define OP_DIV 0x08
+#define OP_DIVI 0x09
+#define OP_DIVU 0x0A
+#define OP_DIVUI 0x0B
+#define OP_REM 0x0C
+#define OP_REMI 0x0D
+#define OP_REMU 0x0E
+#define OP_REMUI 0x0F
+
+#define OP_AND 0x10
+#define OP_ANDI 0x11
+#define OP_OR 0x12
+#define OP_ORI 0x13
+#define OP_XOR 0x14
+#define OP_XORI 0x15
+#define OP_XNOR 0x16
+#define OP_XNORI 0x17
+
+#define OP_SLL 0x18
+#define OP_SLLI 0x19
+#define OP_SLR 0x1A
+#define OP_SLRI 0x1B
+#define OP_SAR 0x1C
+#define OP_SARI 0x1D
+
+#define OP_LDHI 0x1F
+
+#define OP_BEQ 0x20
+#define OP_BNE 0x21
+#define OP_BLE 0x22
+#define OP_BLEU 0x23
+#define OP_BLT 0x24
+#define OP_BLTU 0x25
+#define OP_BGE 0x26
+#define OP_BGEU 0x27
+#define OP_BGT 0x28
+#define OP_BGTU 0x29
+
+#define OP_J 0x2A
+#define OP_JR 0x2B
+#define OP_JAL 0x2C
+#define OP_JALR 0x2D
+
+#define OP_TRAP 0x2E
+#define OP_RFX 0x2F
+
+#define OP_LDW 0x30
+#define OP_LDH 0x31
+#define OP_LDHU 0x32
+#define OP_LDB 0x33
+#define OP_LDBU 0x34
+
+#define OP_STW 0x35
+#define OP_STH 0x36
+#define OP_STB 0x37
+
+#define OP_MVFS 0x38
+#define OP_MVTS 0x39
+#define OP_TBS 0x3A
+#define OP_TBWR 0x3B
+#define OP_TBRI 0x3C
+#define OP_TBWI 0x3D
+
+
+typedef struct {
+ char *name;
+ int format;
+ Byte opcode;
+} Instr;
+
+
+extern Instr instrTbl[];
+extern Instr *instrCodeTbl[];
+
+
+void initInstrTable(void);
+Instr *lookupInstr(char *name);
+
+
+#endif /* _INSTR_H_ */
Index: monitor/monitor/boot.h
===================================================================
--- monitor/monitor/boot.h (nonexistent)
+++ monitor/monitor/boot.h (revision 16)
@@ -0,0 +1,18 @@
+/*
+ * boot.h -- bootstrap from disk
+ */
+
+
+#ifndef _BOOT_H_
+#define _BOOT_H_
+
+
+#define PHYS_BOOT 0x00000000 /* where to load the bootstrap */
+#define VIRT_BOOT 0xC0000000 /* where to start the bootstrap */
+#define TOS_BOOT 0xC0001000 /* top of stack for bootstrap */
+
+
+void boot(int dskno);
+
+
+#endif /* _BOOT_H_ */
Index: monitor/monitor/start.s
===================================================================
--- monitor/monitor/start.s (nonexistent)
+++ monitor/monitor/start.s (revision 16)
@@ -0,0 +1,389 @@
+;
+; start.s -- ECO32 ROM monitor startup and support routines
+;
+
+ .set dmapaddr,0xC0000000 ; base of directly mapped addresses
+ .set stacktop,0xC0400000 ; monitor stack is at top of memory
+
+ .set PSW,0 ; reg # of PSW
+ .set TLB_INDEX,1 ; reg # of TLB Index
+ .set TLB_ENTRY_HI,2 ; reg # of TLB EntryHi
+ .set TLB_ENTRY_LO,3 ; reg # of TLB EntryLo
+ .set TLB_ENTRIES,32 ; number of TLB entries
+
+ .set USER_CONTEXT_SIZE,36*4 ; size of user context
+
+;***************************************************************
+
+ .import _ecode
+ .import _edata
+ .import _ebss
+
+ .import kbdinit
+ .import kbdinchk
+ .import kbdin
+
+ .import dspinit
+ .import dspoutchk
+ .import dspout
+
+ .import serinit
+ .import ser0inchk
+ .import ser0in
+ .import ser0outchk
+ .import ser0out
+
+ .import sctcapctl
+ .import sctioctl
+ .import sctcapser
+ .import sctioser
+
+ .import main
+
+ .export _bcode
+ .export _bdata
+ .export _bbss
+
+ .export cinchk
+ .export cin
+ .export coutchk
+ .export cout
+ .export sinchk
+ .export sin
+ .export soutchk
+ .export sout
+ .export dskcap
+ .export dskio
+
+ .export getTLB_HI
+ .export getTLB_LO
+ .export setTLB
+
+ .export saveState
+ .export monitorReturn
+
+ .import userContext
+ .export resume
+
+;***************************************************************
+
+ .code
+_bcode:
+
+ .data
+_bdata:
+
+ .bss
+_bbss:
+
+;***************************************************************
+
+ .code
+ .align 4
+
+reset:
+ j start
+
+interrupt:
+ j isr
+
+userMiss:
+ j umsr
+
+;***************************************************************
+
+ .code
+ .align 4
+
+cinchk:
+; j kbdinchk
+ j ser0inchk
+
+cin:
+; j kbdin
+ j ser0in
+
+coutchk:
+; j dspoutchk
+ j ser0outchk
+
+cout:
+; j dspout
+ j ser0out
+
+sinchk:
+ j ser0inchk
+
+sin:
+ j ser0in
+
+soutchk:
+ j ser0outchk
+
+sout:
+ j ser0out
+
+dskcap:
+ j dcap
+
+dskio:
+ j dio
+
+;***************************************************************
+
+ .code
+ .align 4
+
+start:
+ ; force CPU into a defined state
+ mvts $0,PSW ; disable interrupts and user mode
+
+ ; initialize TLB
+ mvts $0,TLB_ENTRY_LO ; invalidate all TLB entries
+ add $8,$0,dmapaddr ; by impossible virtual page number
+ add $9,$0,$0
+ add $10,$0,TLB_ENTRIES
+tlbloop:
+ mvts $8,TLB_ENTRY_HI
+ mvts $9,TLB_INDEX
+ tbwi
+ add $8,$8,0x1000 ; all entries must be different
+ add $9,$9,1
+ bne $9,$10,tlbloop
+
+ ; copy data segment
+ add $10,$0,_bdata ; lowest dst addr to be written to
+ add $8,$0,_edata ; one above the top dst addr
+ sub $9,$8,$10 ; $9 = size of data segment
+ add $9,$9,_ecode ; data is waiting right after code
+ j cpytest
+cpyloop:
+ ldw $11,$9,0 ; src addr in $9
+ stw $11,$8,0 ; dst addr in $8
+cpytest:
+ sub $8,$8,4 ; downward
+ sub $9,$9,4
+ bgeu $8,$10,cpyloop
+
+ ; clear bss segment
+ add $8,$0,_bbss ; start with first word of bss
+ add $9,$0,_ebss ; this is one above the top
+ j clrtest
+clrloop:
+ stw $0,$8,0 ; dst addr in $8
+ add $8,$8,4 ; upward
+clrtest:
+ bltu $8,$9,clrloop
+
+ ; now do some useful work
+ add $29,$0,stacktop ; setup monitor stack
+; jal dspinit ; init display
+; jal kbdinit ; init keyboard
+ jal serinit ; init serial interface
+ jal main ; enter command loop
+
+ ; main should never return
+ j start ; just to be sure...
+
+;***************************************************************
+
+ ; Word getTLB_HI(int index)
+getTLB_HI:
+ mvts $4,TLB_INDEX
+ tbri
+ mvfs $2,TLB_ENTRY_HI
+ jr $31
+
+ ; Word getTLB_LO(int index)
+getTLB_LO:
+ mvts $4,TLB_INDEX
+ tbri
+ mvfs $2,TLB_ENTRY_LO
+ jr $31
+
+ ; void setTLB(int index, Word entryHi, Word entryLo)
+setTLB:
+ mvts $4,TLB_INDEX
+ mvts $5,TLB_ENTRY_HI
+ mvts $6,TLB_ENTRY_LO
+ tbwi
+ jr $31
+
+;***************************************************************
+
+ ; int dskcap(int dskno)
+dcap:
+ bne $4,$0,dcapser
+ j sctcapctl
+dcapser:
+ j sctcapser
+
+ ; int dskio(int dskno, char cmd, int sct, Word addr, int nscts)
+dio:
+ bne $4,$0,dioser
+ add $4,$5,$0
+ add $5,$6,$0
+ add $6,$7,$0
+ ldw $7,$29,16
+ j sctioctl
+dioser:
+ add $4,$5,$0
+ add $5,$6,$0
+ add $6,$7,$0
+ ldw $7,$29,16
+ j sctioser
+
+;***************************************************************
+
+ .code
+ .align 4
+
+ ; Bool saveState(MonitorState *msp)
+ ; always return 'true' here
+saveState:
+ stw $31,$4,0*4 ; return address
+ stw $29,$4,1*4 ; stack pointer
+ stw $16,$4,2*4 ; local variables
+ stw $17,$4,3*4
+ stw $18,$4,4*4
+ stw $19,$4,5*4
+ stw $20,$4,6*4
+ stw $21,$4,7*4
+ stw $22,$4,8*4
+ stw $23,$4,9*4
+ add $2,$0,1
+ jr $31
+
+ ; load state when re-entering monitor
+ ; this appears as if returning from saveState
+ ; but the return value is 'false' here
+loadState:
+ ldw $8,$0,monitorReturn
+ beq $8,$0,loadState ; fatal error: monitor state lost
+ ldw $31,$8,0*4 ; return address
+ ldw $29,$8,1*4 ; stack pointer
+ ldw $16,$8,2*4 ; local variables
+ ldw $17,$8,3*4
+ ldw $18,$8,4*4
+ ldw $19,$8,5*4
+ ldw $20,$8,6*4
+ ldw $21,$8,7*4
+ ldw $22,$8,8*4
+ ldw $23,$8,9*4
+ add $2,$0,0
+ jr $31
+
+ .bss
+ .align 4
+
+ ; extern MonitorState *monitorReturn
+monitorReturn:
+ .space 4
+
+ ; extern UserContext userContext
+userContext:
+ .space USER_CONTEXT_SIZE
+
+;***************************************************************
+
+ .code
+ .align 4
+
+ ; void resume(void)
+ ; use userContext to load state
+resume:
+ mvts $0,PSW
+ add $28,$0,userContext
+ .nosyn
+ ldw $8,$28,33*4 ; tlbIndex
+ mvts $8,TLB_INDEX
+ ldw $8,$28,34*4 ; tlbWntryHi
+ mvts $8,TLB_ENTRY_HI
+ ldw $8,$28,35*4 ; tlbEntryLo
+ mvts $8,TLB_ENTRY_LO
+ ;ldw $0,$28,0*4 ; registers
+ ldw $1,$28,1*4
+ ldw $2,$28,2*4
+ ldw $3,$28,3*4
+ ldw $4,$28,4*4
+ ldw $5,$28,5*4
+ ldw $6,$28,6*4
+ ldw $7,$28,7*4
+ ldw $8,$28,8*4
+ ldw $9,$28,9*4
+ ldw $10,$28,10*4
+ ldw $11,$28,11*4
+ ldw $12,$28,12*4
+ ldw $13,$28,13*4
+ ldw $14,$28,14*4
+ ldw $15,$28,15*4
+ ldw $16,$28,16*4
+ ldw $17,$28,17*4
+ ldw $18,$28,18*4
+ ldw $19,$28,19*4
+ ldw $20,$28,20*4
+ ldw $21,$28,21*4
+ ldw $22,$28,22*4
+ ldw $23,$28,23*4
+ ldw $24,$28,24*4
+ ldw $25,$28,25*4
+ ldw $26,$28,26*4
+ ldw $27,$28,27*4
+ ;ldw $28,$28,28*4
+ ldw $29,$28,29*4
+ ldw $30,$28,30*4
+ ldw $31,$28,31*4
+ ldw $28,$28,32*4 ; psw
+ mvts $28,PSW
+ rfx
+ .syn
+
+ ; interrupt entry
+ ; use userContext to store state
+isr:
+umsr:
+ .nosyn
+ ldhi $28,userContext
+ or $28,$28,userContext
+ stw $0,$28,0*4 ; registers
+ stw $1,$28,1*4
+ stw $2,$28,2*4
+ stw $3,$28,3*4
+ stw $4,$28,4*4
+ stw $5,$28,5*4
+ stw $6,$28,6*4
+ stw $7,$28,7*4
+ stw $8,$28,8*4
+ stw $9,$28,9*4
+ stw $10,$28,10*4
+ stw $11,$28,11*4
+ stw $12,$28,12*4
+ stw $13,$28,13*4
+ stw $14,$28,14*4
+ stw $15,$28,15*4
+ stw $16,$28,16*4
+ stw $17,$28,17*4
+ stw $18,$28,18*4
+ stw $19,$28,19*4
+ stw $20,$28,20*4
+ stw $21,$28,21*4
+ stw $22,$28,22*4
+ stw $23,$28,23*4
+ stw $24,$28,24*4
+ stw $25,$28,25*4
+ stw $26,$28,26*4
+ stw $27,$28,27*4
+ stw $28,$28,28*4
+ stw $29,$28,29*4
+ stw $30,$28,30*4
+ stw $31,$28,31*4
+ mvfs $8,PSW
+ stw $8,$28,32*4 ; psw
+ mvfs $8,TLB_INDEX
+ stw $8,$28,33*4 ; tlbIndex
+ mvfs $8,TLB_ENTRY_HI
+ stw $8,$28,34*4 ; tlbEntryHi
+ mvfs $8,TLB_ENTRY_LO
+ stw $8,$28,35*4 ; tlbEntryLo
+ .syn
+ j loadState
Index: monitor/monitor/command.c
===================================================================
--- monitor/monitor/command.c (nonexistent)
+++ monitor/monitor/command.c (revision 16)
@@ -0,0 +1,864 @@
+/*
+ * command.c -- command interpreter
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "getline.h"
+#include "command.h"
+#include "asm.h"
+#include "disasm.h"
+#include "boot.h"
+#include "cpu.h"
+#include "mmu.h"
+#include "start.h"
+
+
+#define MAX_TOKENS 10
+
+
+typedef struct {
+ char *name;
+ void (*hlpProc)(void);
+ void (*cmdProc)(char *tokens[], int n);
+} Command;
+
+extern Command commands[];
+extern int numCommands;
+
+
+static void help(void) {
+ printf("valid commands are:\n");
+ printf(" help get help\n");
+ printf(" + add and subtract\n");
+ printf(" a assemble\n");
+ printf(" u unassemble\n");
+ printf(" b set/reset breakpoint\n");
+ printf(" c continue from breakpoint\n");
+ printf(" s single-step\n");
+ printf(" @ show/set PC\n");
+ printf(" p show/set PSW\n");
+ printf(" r show/set register\n");
+ printf(" d dump memory\n");
+ printf(" mw show/set memory word\n");
+ printf(" mh show/set memory halfword\n");
+ printf(" mb show/set memory byte\n");
+ printf(" t show/set TLB contents\n");
+ printf(" boot bootstrap from disk\n");
+ printf("type 'help ' to get help for \n");
+}
+
+
+static void help00(void) {
+ printf(" help show a list of commands\n");
+ printf(" help show help for \n");
+}
+
+
+static void help01(void) {
+ printf(" + add and subtract and \n");
+}
+
+
+static void help02(void) {
+ printf(" a assemble starting at PC\n");
+ printf(" a assemble starting at \n");
+}
+
+
+static void help03(void) {
+ printf(" u unassemble 16 instrs starting at PC\n");
+ printf(" u unassemble 16 instrs starting at \n");
+ printf(" u unassemble instrs starting at \n");
+}
+
+
+static void help04(void) {
+ printf(" b reset break\n");
+ printf(" b set break at \n");
+}
+
+
+static void help05(void) {
+ printf(" c continue execution\n");
+ printf(" c continue execution times\n");
+}
+
+
+static void help06(void) {
+ printf(" s single-step one instruction\n");
+ printf(" s single-step instructions\n");
+}
+
+
+static void help07(void) {
+ printf(" @ show PC\n");
+ printf(" @ set PC to \n");
+}
+
+
+static void help08(void) {
+ printf(" p show PSW\n");
+ printf(" p set PSW to \n");
+}
+
+
+static void help09(void) {
+ printf(" r show all registers\n");
+ printf(" r show register \n");
+ printf(" r set register to \n");
+}
+
+
+static void help10(void) {
+ printf(" d dump 256 bytes starting at PC\n");
+ printf(" d dump 256 bytes starting at \n");
+ printf(" d dump bytes starting at \n");
+}
+
+
+static void help11(void) {
+ printf(" mw show memory word at PC\n");
+ printf(" mw show memory word at \n");
+ printf(" mw set memory word at to \n");
+}
+
+
+static void help12(void) {
+ printf(" mh show memory halfword at PC\n");
+ printf(" mh show memory halfword at \n");
+ printf(" mh set memory halfword at to \n");
+}
+
+
+static void help13(void) {
+ printf(" mb show memory byte at PC\n");
+ printf(" mb show memory byte at \n");
+ printf(" mb set memory byte at to \n");
+}
+
+
+static void help14(void) {
+ printf(" t show TLB contents\n");
+ printf(" t show TLB contents at \n");
+ printf(" t p set TLB contents at to page \n");
+ printf(" t f set TLB contents at to frame \n");
+}
+
+
+static void help15(void) {
+ printf(" boot load and execute first sector of disk \n");
+}
+
+
+static Bool getHexNumber(char *str, Word *valptr) {
+ char *end;
+
+ *valptr = strtoul(str, &end, 16);
+ return *end == '\0';
+}
+
+
+static Bool getDecNumber(char *str, int *valptr) {
+ char *end;
+
+ *valptr = strtoul(str, &end, 10);
+ return *end == '\0';
+}
+
+
+static void showPC(void) {
+ Word pc, psw;
+ Word instr;
+
+ pc = cpuGetPC();
+ psw = cpuGetPSW();
+ instr = mmuReadWord(pc);
+ printf("PC %08X [PC] %08X %s\n",
+ pc, instr, disasm(instr, pc));
+}
+
+
+static void showBreak(void) {
+ Word brk;
+
+ brk = cpuGetBreak();
+ printf("Brk ");
+ if (cpuTestBreak()) {
+ printf("%08X", brk);
+ } else {
+ printf("--------");
+ }
+ printf("\n");
+}
+
+
+static void showPSW(void) {
+ Word psw;
+ int i;
+
+ psw = cpuGetPSW();
+ printf(" xxxx V UPO IPO IACK MASK\n");
+ printf("PSW ");
+ for (i = 31; i >= 0; i--) {
+ if (i == 27 || i == 26 || i == 23 || i == 20 || i == 15) {
+ printf(" ");
+ }
+ printf("%c", psw & (1 << i) ? '1' : '0');
+ }
+ printf("\n");
+}
+
+
+static void doHelp(char *tokens[], int n) {
+ int i;
+
+ if (n == 1) {
+ help();
+ } else if (n == 2) {
+ for (i = 0; i < numCommands; i++) {
+ if (strcmp(commands[i].name, tokens[1]) == 0) {
+ (*commands[i].hlpProc)();
+ return;
+ }
+ }
+ printf("no help available for '%s', sorry\n", tokens[1]);
+ } else {
+ help00();
+ }
+}
+
+
+static void doArith(char *tokens[], int n) {
+ Word num1, num2, num3, num4;
+
+ if (n == 3) {
+ if (!getHexNumber(tokens[1], &num1)) {
+ printf("illegal first number\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &num2)) {
+ printf("illegal second number\n");
+ return;
+ }
+ num3 = num1 + num2;
+ num4 = num1 - num2;
+ printf("add = %08X, sub = %08X\n", num3, num4);
+ } else {
+ help01();
+ }
+}
+
+
+static void doAssemble(char *tokens[], int n) {
+ Word addr;
+ Word psw;
+ char prompt[30];
+ char *line;
+ char *msg;
+ Word instr;
+
+ if (n == 1) {
+ addr = cpuGetPC();
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ } else {
+ help02();
+ return;
+ }
+ addr &= ~0x00000003;
+ psw = cpuGetPSW();
+ while (1) {
+ sprintf(prompt, "ASM @ %08X: ", addr);
+ line = getLine(prompt);
+ if (*line == '\0' || *line == '\n') {
+ break;
+ }
+ addHist(line);
+ msg = asmInstr(line, addr, &instr);
+ if (msg != NULL) {
+ printf("%s\n", msg);
+ } else {
+ mmuWriteWord(addr, instr);
+ addr += 4;
+ }
+ }
+}
+
+
+static void doUnassemble(char *tokens[], int n) {
+ Word addr, count;
+ Word psw;
+ int i;
+ Word instr;
+
+ if (n == 1) {
+ addr = cpuGetPC();
+ count = 16;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ count = 16;
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &count)) {
+ printf("illegal count\n");
+ return;
+ }
+ if (count == 0) {
+ return;
+ }
+ } else {
+ help03();
+ return;
+ }
+ addr &= ~0x00000003;
+ psw = cpuGetPSW();
+ for (i = 0; i < count; i++) {
+ instr = mmuReadWord(addr);
+ printf("%08X: %08X %s\n",
+ addr, instr, disasm(instr, addr));
+ if (addr + 4 < addr) {
+ /* wrap-around */
+ break;
+ }
+ addr += 4;
+ }
+}
+
+
+static void doBreak(char *tokens[], int n) {
+ Word addr;
+
+ if (n == 1) {
+ cpuResetBreak();
+ showBreak();
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ addr &= ~0x00000003;
+ cpuSetBreak(addr);
+ showBreak();
+ } else {
+ help04();
+ }
+}
+
+
+static void doContinue(char *tokens[], int n) {
+ Word count, i;
+ Word addr;
+
+ if (n == 1) {
+ count = 1;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &count) || count == 0) {
+ printf("illegal count\n");
+ return;
+ }
+ } else {
+ help05();
+ return;
+ }
+ for (i = 0; i < count; i++) {
+ cpuRun();
+ }
+ addr = cpuGetPC();
+ printf("Break at %08X\n", addr);
+ showPC();
+}
+
+
+static void doStep(char *tokens[], int n) {
+ Word count, i;
+
+ if (n == 1) {
+ count = 1;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &count) || count == 0) {
+ printf("illegal count\n");
+ return;
+ }
+ } else {
+ help06();
+ return;
+ }
+ for (i = 0; i < count; i++) {
+ cpuStep();
+ }
+ showPC();
+}
+
+
+static void doPC(char *tokens[], int n) {
+ Word addr;
+
+ if (n == 1) {
+ showPC();
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ addr &= ~0x00000003;
+ cpuSetPC(addr);
+ showPC();
+ } else {
+ help07();
+ }
+}
+
+
+static void explainPSW(Word data) {
+ int i;
+
+ printf("interrupt vector : %s (%s)\n",
+ data & PSW_V ? "on " : "off",
+ data & PSW_V ? "RAM" : "ROM");
+ printf("current user mode : %s (%s)\n",
+ data & PSW_UM ? "on " : "off",
+ data & PSW_UM ? "user" : "kernel");
+ printf("previous user mode : %s (%s)\n",
+ data & PSW_PUM ? "on " : "off",
+ data & PSW_PUM ? "user" : "kernel");
+ printf("old user mode : %s (%s)\n",
+ data & PSW_OUM ? "on " : "off",
+ data & PSW_OUM ? "user" : "kernel");
+ printf("current interrupt enable : %s (%s)\n",
+ data & PSW_IE ? "on " : "off",
+ data & PSW_IE ? "enabled" : "disabled");
+ printf("previous interrupt enable : %s (%s)\n",
+ data & PSW_PIE ? "on " : "off",
+ data & PSW_PIE ? "enabled" : "disabled");
+ printf("old interrupt enable : %s (%s)\n",
+ data & PSW_OIE ? "on " : "off",
+ data & PSW_OIE ? "enabled" : "disabled");
+ printf("last interrupt acknowledged : %02X (%s)\n",
+ (data & PSW_PRIO_MASK) >> 16,
+ exceptionToString((data & PSW_PRIO_MASK) >> 16));
+ for (i = 15; i >= 0; i--) {
+ printf("%-35s: %s (%s)\n",
+ exceptionToString(i),
+ data & (1 << i) ? "on " : "off",
+ data & (1 << i) ? "enabled" : "disabled");
+ }
+}
+
+
+static void doPSW(char *tokens[], int n) {
+ Word data;
+
+ if (n == 1) {
+ data = cpuGetPSW();
+ showPSW();
+ explainPSW(data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &data)) {
+ printf("illegal data\n");
+ return;
+ }
+ data &= 0x0FFFFFFF;
+ cpuSetPSW(data);
+ showPSW();
+ explainPSW(data);
+ } else {
+ help08();
+ }
+}
+
+
+static void doRegister(char *tokens[], int n) {
+ int i, j;
+ int reg;
+ Word data;
+
+ if (n == 1) {
+ for (i = 0; i < 8; i++) {
+ for (j = 0; j < 4; j++) {
+ reg = 8 * j + i;
+ data = cpuGetReg(reg);
+ printf("$%-2d %08X ", reg, data);
+ }
+ printf("\n");
+ }
+ showPSW();
+ showBreak();
+ showPC();
+ } else if (n == 2) {
+ if (!getDecNumber(tokens[1], ®) || reg < 0 || reg >= 32) {
+ printf("illegal register number\n");
+ return;
+ }
+ data = cpuGetReg(reg);
+ printf("$%-2d %08X\n", reg, data);
+ } else if (n == 3) {
+ if (!getDecNumber(tokens[1], ®) || reg < 0 || reg >= 32) {
+ printf("illegal register number\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &data)) {
+ printf("illegal data\n");
+ return;
+ }
+ cpuSetReg(reg, data);
+ } else {
+ help09();
+ }
+}
+
+
+static void doDump(char *tokens[], int n) {
+ Word addr, count;
+ Word psw;
+ Word lo, hi, curr;
+ int lines, i, j;
+ Word tmp;
+ Byte c;
+
+ if (n == 1) {
+ addr = cpuGetPC();
+ count = 16 * 16;
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ count = 16 * 16;
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &count)) {
+ printf("illegal count\n");
+ return;
+ }
+ if (count == 0) {
+ return;
+ }
+ } else {
+ help10();
+ return;
+ }
+ psw = cpuGetPSW();
+ lo = addr & ~0x0000000F;
+ hi = addr + count - 1;
+ if (hi < lo) {
+ /* wrap-around */
+ hi = 0xFFFFFFFF;
+ }
+ lines = (hi - lo + 16) >> 4;
+ curr = lo;
+ for (i = 0; i < lines; i++) {
+ printf("%08X: ", curr);
+ for (j = 0; j < 16; j++) {
+ tmp = curr + j;
+ if (tmp < addr || tmp > hi) {
+ printf(" ");
+ } else {
+ c = mmuReadByte(tmp);
+ printf("%02X", c);
+ }
+ printf(" ");
+ }
+ printf(" ");
+ for (j = 0; j < 16; j++) {
+ tmp = curr + j;
+ if (tmp < addr || tmp > hi) {
+ printf(" ");
+ } else {
+ c = mmuReadByte(tmp);
+ if (c >= 32 && c <= 126) {
+ printf("%c", c);
+ } else {
+ printf(".");
+ }
+ }
+ }
+ printf("\n");
+ curr += 16;
+ }
+}
+
+
+static void doMemoryWord(char *tokens[], int n) {
+ Word psw;
+ Word addr;
+ Word data;
+ Word tmpData;
+
+ psw = cpuGetPSW();
+ if (n == 1) {
+ addr = cpuGetPC();
+ data = mmuReadWord(addr);
+ printf("%08X: %08X\n", addr, data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ data = mmuReadWord(addr);
+ printf("%08X: %08X\n", addr, data);
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &tmpData)) {
+ printf("illegal data\n");
+ return;
+ }
+ data = tmpData;
+ mmuWriteWord(addr, data);
+ } else {
+ help11();
+ }
+}
+
+
+static void doMemoryHalf(char *tokens[], int n) {
+ Word psw;
+ Word addr;
+ Half data;
+ Word tmpData;
+
+ psw = cpuGetPSW();
+ if (n == 1) {
+ addr = cpuGetPC();
+ data = mmuReadHalf(addr);
+ printf("%08X: %04X\n", addr, data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ data = mmuReadHalf(addr);
+ printf("%08X: %04X\n", addr, data);
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &tmpData)) {
+ printf("illegal data\n");
+ return;
+ }
+ data = (Half) tmpData;
+ mmuWriteHalf(addr, data);
+ } else {
+ help12();
+ }
+}
+
+
+static void doMemoryByte(char *tokens[], int n) {
+ Word psw;
+ Word addr;
+ Byte data;
+ Word tmpData;
+
+ psw = cpuGetPSW();
+ if (n == 1) {
+ addr = cpuGetPC();
+ data = mmuReadByte(addr);
+ printf("%08X: %02X\n", addr, data);
+ } else if (n == 2) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ data = mmuReadByte(addr);
+ printf("%08X: %02X\n", addr, data);
+ } else if (n == 3) {
+ if (!getHexNumber(tokens[1], &addr)) {
+ printf("illegal address\n");
+ return;
+ }
+ if (!getHexNumber(tokens[2], &tmpData)) {
+ printf("illegal data\n");
+ return;
+ }
+ data = (Byte) tmpData;
+ mmuWriteByte(addr, data);
+ } else {
+ help13();
+ }
+}
+
+
+static void doTLB(char *tokens[], int n) {
+ int index;
+ TLB_Entry tlbEntry;
+ Word data;
+
+ if (n == 1) {
+ for (index = 0; index < TLB_SIZE; index++) {
+ tlbEntry = mmuGetTLB(index);
+ printf("TLB[%02d] page %08X frame %08X %c %c\n",
+ index, tlbEntry.page, tlbEntry.frame,
+ tlbEntry.write ? 'w' : '-',
+ tlbEntry.valid ? 'v' : '-');
+ }
+ printf("Index(1) %08X\n", mmuGetIndex());
+ printf("EntryHi(2) %08X\n", mmuGetEntryHi());
+ printf("EntryLo(3) %08X\n", mmuGetEntryLo());
+ } else if (n == 2) {
+ if (!getDecNumber(tokens[1], &index) || index < 0 || index >= TLB_SIZE) {
+ printf("illegal TLB index\n");
+ return;
+ }
+ tlbEntry = mmuGetTLB(index);
+ printf("TLB[%02d] page %08X frame %08X %c %c\n",
+ index, tlbEntry.page, tlbEntry.frame,
+ tlbEntry.write ? 'w' : '-',
+ tlbEntry.valid ? 'v' : '-');
+ } else if (n == 3) {
+ help14();
+ } else if (n == 4) {
+ if (!getDecNumber(tokens[1], &index) || index < 0 || index >= TLB_SIZE) {
+ printf("illegal TLB index\n");
+ return;
+ }
+ if (!getHexNumber(tokens[3], &data)) {
+ printf("illegal data\n");
+ return;
+ }
+ tlbEntry = mmuGetTLB(index);
+ if (strcmp(tokens[2], "p") == 0) {
+ tlbEntry.page = data & PAGE_MASK;
+ } else
+ if (strcmp(tokens[2], "f") == 0) {
+ tlbEntry.frame = data & PAGE_MASK;
+ tlbEntry.write = data & TLB_WRITE ? true : false;
+ tlbEntry.valid = data & TLB_VALID ? true : false;
+ } else {
+ printf("TLB selector is not one of 'p' or 'f'\n");
+ return;
+ }
+ mmuSetTLB(index, tlbEntry);
+ printf("TLB[%02d] page %08X frame %08X %c %c\n",
+ index, tlbEntry.page, tlbEntry.frame,
+ tlbEntry.write ? 'w' : '-',
+ tlbEntry.valid ? 'v' : '-');
+ } else {
+ help14();
+ }
+}
+
+
+static void doBoot(char *tokens[], int n) {
+ int dskno;
+
+ if (n == 2) {
+ if (!getDecNumber(tokens[1], &dskno) || dskno < 0 || dskno > 1) {
+ printf("illegal disk number\n");
+ return;
+ }
+ boot(dskno);
+ } else {
+ help15();
+ }
+}
+
+
+Command commands[] = {
+ { "help", help00, doHelp },
+ { "+", help01, doArith },
+ { "a", help02, doAssemble },
+ { "u", help03, doUnassemble },
+ { "b", help04, doBreak },
+ { "c", help05, doContinue },
+ { "s", help06, doStep },
+ { "@", help07, doPC },
+ { "p", help08, doPSW },
+ { "r", help09, doRegister },
+ { "d", help10, doDump },
+ { "mw", help11, doMemoryWord },
+ { "mh", help12, doMemoryHalf },
+ { "mb", help13, doMemoryByte },
+ { "t", help14, doTLB },
+ { "boot", help15, doBoot },
+};
+
+int numCommands = sizeof(commands) / sizeof(commands[0]);
+
+
+static void doCommand(char *line) {
+ char *tokens[MAX_TOKENS];
+ int n;
+ char *p;
+ int i;
+
+ n = 0;
+ p = strtok(line, " \t\n");
+ while (p != NULL) {
+ if (n == MAX_TOKENS) {
+ printf("too many tokens on line\n");
+ return;
+ }
+ tokens[n++] = p;
+ p = strtok(NULL, " \t\n");
+ }
+ if (n == 0) {
+ return;
+ }
+ for (i = 0; i < numCommands; i++) {
+ if (strcmp(commands[i].name, tokens[0]) == 0) {
+ (*commands[i].cmdProc)(tokens, n);
+ return;
+ }
+ }
+ help();
+}
+
+
+static char *article(char firstLetterOfNoun) {
+ switch (firstLetterOfNoun) {
+ case 'a':
+ case 'e':
+ case 'i':
+ case 'o':
+ case 'u':
+ return "An";
+ default:
+ return "A";
+ }
+}
+
+
+static void interactiveException(int exception) {
+ char *what;
+
+ what = exceptionToString(exception);
+ printf("\n");
+ printf("NOTE: %s %s occurred while executing the command.\n",
+ article(*what), what);
+ printf(" This event will not alter the state of the CPU.\n");
+}
+
+
+void execCommand(char *line) {
+ MonitorState commandState;
+
+ if (saveState(&commandState)) {
+ /* initialization */
+ monitorReturn = &commandState;
+ doCommand(line);
+ } else {
+ /* an exception was thrown */
+ interactiveException((userContext.psw & PSW_PRIO_MASK) >> 16);
+ }
+ monitorReturn = NULL;
+}
Index: monitor/monitor/asm.c
===================================================================
--- monitor/monitor/asm.c (nonexistent)
+++ monitor/monitor/asm.c (revision 16)
@@ -0,0 +1,370 @@
+/*
+ * asm.c -- assembler
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "instr.h"
+#include "asm.h"
+
+
+#define MAX_TOKENS 10
+
+
+static char *msgs[] = {
+ /* 0 */ "too many tokens on line",
+ /* 1 */ "empty line",
+ /* 2 */ "unknown instruction name",
+ /* 3 */ "unknown instruction format",
+ /* 4 */ "excess tokens on line",
+ /* 5 */ "too few operands",
+ /* 6 */ "illegal register",
+ /* 7 */ "illegal immediate value",
+ /* 8 */ "immediate value out of range",
+ /* 9 */ "target is not aligned",
+ /* 10 */ "target cannot be reached"
+};
+
+
+static Bool asmReg(char *token, int *reg) {
+ char *end;
+
+ if (*token != '$') {
+ return false;
+ }
+ *reg = strtoul(token + 1, &end, 10);
+ if (*end != '\0') {
+ return false;
+ }
+ if (*reg < 0 || *reg >= 32) {
+ return false;
+ }
+ return true;
+}
+
+
+static Bool asmNum(char *token, unsigned int *val) {
+ char *end;
+
+ *val = strtoul(token, &end, 16);
+ return *end == '\0';
+}
+
+
+char *asmInstr(char *line, Word addr, Word *instrPtr) {
+ char *tokens[MAX_TOKENS];
+ int n;
+ char *p;
+ Instr *instr;
+ Word result;
+ int r1, r2, r3;
+ unsigned int uimm;
+ signed int simm;
+
+ /* separate tokens */
+ n = 0;
+ p = strtok(line, " \t\n,");
+ while (p != NULL) {
+ if (n == MAX_TOKENS) {
+ return msgs[0];
+ }
+ tokens[n++] = p;
+ p = strtok(NULL, " \t\n,");
+ }
+ if (n == 0) {
+ return msgs[1];
+ }
+ /* lookup mnemonic */
+ instr = lookupInstr(tokens[0]);
+ if (instr == NULL) {
+ return msgs[2];
+ }
+ /* do processing according to format */
+ switch (instr->format) {
+ case FORMAT_N:
+ /* no operands (but may get a constant operand) */
+ if (n > 2) {
+ return msgs[4];
+ }
+ if (n < 1) {
+ return msgs[5];
+ }
+ if (n == 2) {
+ if (!asmNum(tokens[1], &uimm)) {
+ return msgs[7];
+ }
+ } else {
+ uimm = 0;
+ }
+ result = ((Word) instr->opcode << 26) |
+ (uimm & MASK(26));
+ break;
+ case FORMAT_RH:
+ /* one register and a half operand */
+ if (n > 3) {
+ return msgs[4];
+ }
+ if (n < 3) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[2], &uimm)) {
+ return msgs[7];
+ }
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ break;
+ case FORMAT_RHH:
+ /* one register and a half operand */
+ /* ATTENTION: high-order 16 bits encoded */
+ if (n > 3) {
+ return msgs[4];
+ }
+ if (n < 3) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[2], &uimm)) {
+ return msgs[7];
+ }
+ uimm >>= 16;
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ break;
+ case FORMAT_RRH:
+ /* two registers and a half operand */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[3], &uimm)) {
+ return msgs[7];
+ }
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ break;
+ case FORMAT_RRS:
+ /* two registers and a signed half operand */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[3], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if (simm >= (signed) (1 << 15) ||
+ simm < - (signed) (1 << 15)) {
+ return msgs[8];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (simm & MASK(16));
+ break;
+ case FORMAT_RRR:
+ /* three register operands */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[3], &r3)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r3 << 16) |
+ (r1 << 11);
+ break;
+ case FORMAT_RRX:
+ /* either FORMAT_RRR or FORMAT_RRH */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (*tokens[3] == '$') {
+ /* FORMAT_RRR */
+ if (!asmReg(tokens[3], &r3)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r3 << 16) |
+ (r1 << 11);
+ } else {
+ /* FORMAT_RRH */
+ if (!asmNum(tokens[3], &uimm)) {
+ return msgs[7];
+ }
+ if (uimm >= (unsigned) (1 << 16)) {
+ return msgs[8];
+ }
+ result = (((Word) instr->opcode + 1) << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (uimm & MASK(16));
+ }
+ break;
+ case FORMAT_RRY:
+ /* either FORMAT_RRR or FORMAT_RRS */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (*tokens[3] == '$') {
+ /* FORMAT_RRR */
+ if (!asmReg(tokens[3], &r3)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r2 << 21) |
+ (r3 << 16) |
+ (r1 << 11);
+ } else {
+ /* FORMAT_RRS */
+ if (!asmNum(tokens[3], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if (simm >= (signed) (1 << 15) ||
+ simm < - (signed) (1 << 15)) {
+ return msgs[8];
+ }
+ result = (((Word) instr->opcode + 1) << 26) |
+ (r2 << 21) |
+ (r1 << 16) |
+ (simm & MASK(16));
+ }
+ break;
+ case FORMAT_RRB:
+ /* two registers and a 16 bit signed offset operand */
+ if (n > 4) {
+ return msgs[4];
+ }
+ if (n < 4) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ if (!asmReg(tokens[2], &r2)) {
+ return msgs[6];
+ }
+ if (!asmNum(tokens[3], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if ((simm & 0x00000003) != 0) {
+ return msgs[9];
+ }
+ simm -= addr + 4;
+ simm /= 4;
+ if (simm >= (signed) (1 << 15) ||
+ simm < - (signed) (1 << 15)) {
+ return msgs[10];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 21) |
+ (r2 << 16) |
+ (simm & MASK(16));
+ break;
+ case FORMAT_J:
+ /* no registers and a 26 bit signed offset operand */
+ if (n > 2) {
+ return msgs[4];
+ }
+ if (n < 2) {
+ return msgs[5];
+ }
+ if (!asmNum(tokens[1], (unsigned int *) &simm)) {
+ return msgs[7];
+ }
+ if ((simm & 0x00000003) != 0) {
+ return msgs[9];
+ }
+ simm -= addr + 4;
+ simm /= 4;
+ if (simm >= (signed) (1 << 25) ||
+ simm < - (signed) (1 << 25)) {
+ return msgs[10];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (simm & MASK(26));
+ break;
+ case FORMAT_JR:
+ /* one register operand */
+ if (n > 2) {
+ return msgs[4];
+ }
+ if (n < 2) {
+ return msgs[5];
+ }
+ if (!asmReg(tokens[1], &r1)) {
+ return msgs[6];
+ }
+ result = ((Word) instr->opcode << 26) |
+ (r1 << 21);
+ break;
+ default:
+ return msgs[3];
+ }
+ /* line successfully assembled */
+ *instrPtr = result;
+ return NULL;
+}
Index: monitor/monitor/keyboard.s
===================================================================
--- monitor/monitor/keyboard.s (nonexistent)
+++ monitor/monitor/keyboard.s (revision 16)
@@ -0,0 +1,140 @@
+;
+; keyboard.s -- a PC keyboard as input device
+;
+
+;***************************************************************
+
+ .set kbdbase,0xF0200000 ; keyboard base address
+
+; .import cout
+; .import byteout
+
+ .import xltbl1 ; kbd translation table 1
+ .import xltbl2 ; kbd translation table 2
+
+ .export kbdinit ; initialize keyboard
+ .export kbdinchk ; check if input available
+ .export kbdin ; do keyboard input
+
+;***************************************************************
+
+ .code
+ .align 4
+
+kbdinit:
+ jr $31
+
+kbdinchk:
+ add $8,$0,kbdbase
+ ldw $2,$8,0
+ and $2,$2,1
+ jr $31
+
+kbdin:
+ sub $29,$29,12
+ stw $31,$29,8
+ stw $16,$29,4
+ stw $17,$29,0
+kbdin0:
+ jal kbdinp
+ add $16,$2,$0 ; key1 in $16
+ add $8,$0,0xF0
+ bne $16,$8,kbdin2
+kbdin1:
+ jal kbdinp
+ j kbdin0
+kbdin2:
+ jal kbdinp
+ add $17,$2,$0 ; key2 in $17
+ beq $17,$16,kbdin2
+ add $8,$0,0xF0
+ beq $17,$8,kbdin3
+ j kbdin5
+kbdin3:
+ jal kbdinp
+ bne $2,$16,kbdin2
+kbdin4:
+ add $4,$16,$0
+ add $5,$0,xltbl1
+ jal xlat
+ j kbdx
+kbdin5:
+ jal kbdinp
+ add $8,$0,0xF0
+ bne $2,$8,kbdin5
+kbdin6:
+ jal kbdinp
+ beq $2,$16,kbdin7
+ beq $2,$17,kbdin9
+ j kbdin5
+kbdin7:
+ jal kbdinp
+ add $8,$0,0xF0
+ bne $2,$8,kbdin7
+kbdin8:
+ jal kbdinp
+ bne $2,$17,kbdin7
+ j kbdin11
+kbdin9:
+ jal kbdinp
+ add $8,$0,0xF0
+ bne $2,$8,kbdin9
+kbdin10:
+ jal kbdinp
+ bne $2,$16,kbdin9
+ j kbdin11
+kbdin11:
+ add $8,$0,0x12 ; left shift key
+ beq $16,$8,kbdin12
+ add $8,$0,0x59 ; right shift key
+ bne $16,$8,kbdin13
+kbdin12:
+ add $4,$17,$0
+ add $5,$0,xltbl2
+ jal xlat
+ j kbdx
+kbdin13:
+ add $4,$16,$0
+ add $5,$0,xltbl1
+ jal xlat
+ j kbdx
+kbdx:
+ ldw $17,$29,0
+ ldw $16,$29,4
+ ldw $31,$29,8
+ add $29,$29,12
+ jr $31
+
+kbdinp:
+ add $8,$0,kbdbase
+kbdinp1:
+ ldw $9,$8,0
+ and $9,$9,1
+ beq $9,$0,kbdinp1
+ ldw $2,$8,4
+ add $9,$0,0xE0
+ beq $2,$9,kbdinp1
+ add $9,$0,0xE1
+ beq $2,$9,kbdinp1
+ jr $31
+
+xlat:
+ sub $29,$29,8
+ stw $31,$29,4
+ stw $16,$29,0
+ and $16,$4,0xFF
+ add $8,$16,$5
+ ldbu $2,$8,0
+ bne $2,$0,xlat1
+; add $4,$0,'<'
+; jal cout
+; add $4,$16,$0
+; jal byteout
+; add $4,$0,'>'
+; jal cout
+ add $2,$16,$0
+xlat1:
+ ldw $16,$29,0
+ ldw $31,$29,4
+ add $29,$29,8
+ jr $31
Index: monitor/monitor/disasm.c
===================================================================
--- monitor/monitor/disasm.c (nonexistent)
+++ monitor/monitor/disasm.c (revision 16)
@@ -0,0 +1,138 @@
+/*
+ * disasm.c -- disassembler
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "instr.h"
+#include "disasm.h"
+
+
+static char instrBuffer[100];
+
+
+static void disasmN(char *opName, Word immed) {
+ if (immed == 0) {
+ sprintf(instrBuffer, "%-7s", opName);
+ } else {
+ sprintf(instrBuffer, "%-7s %08X", opName, immed);
+ }
+}
+
+
+static void disasmRH(char *opName, int r1, Half immed) {
+ sprintf(instrBuffer, "%-7s $%d,%04X", opName, r1, immed);
+}
+
+
+static void disasmRHH(char *opName, int r1, Half immed) {
+ sprintf(instrBuffer, "%-7s $%d,%08X", opName, r1, (Word) immed << 16);
+}
+
+
+static void disasmRRH(char *opName, int r1, int r2, Half immed) {
+ sprintf(instrBuffer, "%-7s $%d,$%d,%04X", opName, r1, r2, immed);
+}
+
+
+static void disasmRRS(char *opName, int r1, int r2, Half immed) {
+ sprintf(instrBuffer, "%-7s $%d,$%d,%s%04X", opName, r1, r2,
+ SIGN(16) & immed ? "-" : "+",
+ SIGN(16) & immed ? -(signed)SEXT16(immed) : SEXT16(immed));
+}
+
+
+static void disasmRRR(char *opName, int r1, int r2, int r3) {
+ sprintf(instrBuffer, "%-7s $%d,$%d,$%d", opName, r1, r2, r3);
+}
+
+
+static void disasmRRB(char *opName, int r1, int r2, Half offset, Word locus) {
+ sprintf(instrBuffer, "%-7s $%d,$%d,%08X", opName,
+ r1, r2, (locus + 4) + (SEXT16(offset) << 2));
+}
+
+
+static void disasmJ(char *opName, Word offset, Word locus) {
+ sprintf(instrBuffer, "%-7s %08X", opName,
+ (locus + 4) + (SEXT26(offset) << 2));
+}
+
+
+static void disasmJR(char *opName, int r1) {
+ sprintf(instrBuffer, "%-7s $%d", opName, r1);
+}
+
+
+char *disasm(Word instr, Word locus) {
+ Byte opcode;
+ Instr *ip;
+
+ opcode = (instr >> 26) & 0x3F;
+ ip = instrCodeTbl[opcode];
+ if (ip == NULL) {
+ disasmN("???", 0);
+ } else {
+ switch (ip->format) {
+ case FORMAT_N:
+ disasmN(ip->name, instr & 0x03FFFFFF);
+ break;
+ case FORMAT_RH:
+ disasmRH(ip->name, (instr >> 16) & 0x1F, instr & 0x0000FFFF);
+ break;
+ case FORMAT_RHH:
+ disasmRHH(ip->name, (instr >> 16) & 0x1F, instr & 0x0000FFFF);
+ break;
+ case FORMAT_RRH:
+ disasmRRH(ip->name, (instr >> 16) & 0x1F,
+ (instr >> 21) & 0x1F, instr & 0x0000FFFF);
+ break;
+ case FORMAT_RRS:
+ disasmRRS(ip->name, (instr >> 16) & 0x1F,
+ (instr >> 21) & 0x1F, instr & 0x0000FFFF);
+ break;
+ case FORMAT_RRR:
+ disasmRRR(ip->name, (instr >> 11) & 0x1F,
+ (instr >> 21) & 0x1F, (instr >> 16) & 0x1F);
+ break;
+ case FORMAT_RRX:
+ if ((opcode & 1) == 0) {
+ /* the FORMAT_RRR variant */
+ disasmRRR(ip->name, (instr >> 11) & 0x1F,
+ (instr >> 21) & 0x1F, (instr >> 16) & 0x1F);
+ } else {
+ /* the FORMAT_RRH variant */
+ disasmRRH(ip->name, (instr >> 16) & 0x1F,
+ (instr >> 21) & 0x1F, instr & 0x0000FFFF);
+ }
+ break;
+ case FORMAT_RRY:
+ if ((opcode & 1) == 0) {
+ /* the FORMAT_RRR variant */
+ disasmRRR(ip->name, (instr >> 11) & 0x1F,
+ (instr >> 21) & 0x1F, (instr >> 16) & 0x1F);
+ } else {
+ /* the FORMAT_RRS variant */
+ disasmRRS(ip->name, (instr >> 16) & 0x1F,
+ (instr >> 21) & 0x1F, instr & 0x0000FFFF);
+ }
+ break;
+ case FORMAT_RRB:
+ disasmRRB(ip->name, (instr >> 21) & 0x1F,
+ (instr >> 16) & 0x1F, instr & 0x0000FFFF, locus);
+ break;
+ case FORMAT_J:
+ disasmJ(ip->name, instr & 0x03FFFFFF, locus);
+ break;
+ case FORMAT_JR:
+ disasmJR(ip->name, (instr >> 21) & 0x1F);
+ break;
+ default:
+ printf("illegal entry in instruction table\n");
+ break;
+ }
+ }
+ return instrBuffer;
+}
Index: monitor/monitor/sctio-ctl.s
===================================================================
--- monitor/monitor/sctio-ctl.s (nonexistent)
+++ monitor/monitor/sctio-ctl.s (revision 16)
@@ -0,0 +1,133 @@
+;
+; sctio-ctl.s -- disk sector I/O for disk made available by disk controller
+;
+
+;***************************************************************
+
+ .set dskbase,0xF0400000 ; disk base address
+ .set dskctrl,0 ; control register
+ .set dskcnt,4 ; count register
+ .set dsksct,8 ; sector register
+ .set dskcap,12 ; capacity register
+ .set dskbuf,0x00080000 ; disk buffer
+
+ .set ctrlstrt,0x01 ; start bit
+ .set ctrlien,0x02 ; interrupt enable bit
+ .set ctrlwrt,0x04 ; write bit
+ .set ctrlerr,0x08 ; error bit
+ .set ctrldone,0x10 ; done bit
+ .set ctrlrdy,0x20 ; ready bit
+
+ .set sctsize,512 ; sector size in bytes
+
+ .set retries,1000000 ; retries to get disk ready
+
+ .export sctcapctl ; determine disk capacity
+ .export sctioctl ; do disk I/O
+
+;***************************************************************
+
+ .code
+ .align 4
+
+sctcapctl:
+ add $8,$0,retries ; set retry count
+ add $9,$0,dskbase
+sctcap1:
+ ldw $10,$9,dskctrl
+ and $10,$10,ctrlrdy ; ready?
+ bne $10,$0,sctcapok ; yes - jump
+ sub $8,$8,1
+ bne $8,$0,sctcap1 ; try again
+ add $2,$0,0 ; no disk found
+ j sctcapx
+sctcapok:
+ ldw $2,$9,dskcap ; get disk capacity
+sctcapx:
+ jr $31
+
+sctioctl:
+ sub $29,$29,24
+ stw $31,$29,20
+ stw $16,$29,16
+ stw $17,$29,12
+ stw $18,$29,8
+ stw $19,$29,4
+ stw $20,$29,0
+ add $16,$4,$0 ; command
+ add $17,$5,$0 ; sector number
+ add $18,$6,0xC0000000 ; memory address, virtualized
+ add $19,$7,$0 ; number of sectors
+
+ add $8,$0,'r'
+ beq $16,$8,sctrd
+ add $8,$0,'w'
+ beq $16,$8,sctwr
+ add $2,$0,0xFF ; illegal command
+ j sctx
+
+sctrd:
+ add $2,$0,$0 ; return ok
+ beq $19,$0,sctx ; if no (more) sectors
+ add $8,$0,dskbase
+ add $9,$0,1
+ stw $9,$8,dskcnt ; number of sectors
+ stw $17,$8,dsksct ; sector number on disk
+ add $9,$0,ctrlstrt
+ stw $9,$8,dskctrl ; start command
+sctrd1:
+ ldw $2,$8,dskctrl
+ and $9,$2,ctrldone ; done?
+ beq $9,$0,sctrd1 ; no - wait
+ and $9,$2,ctrlerr ; error?
+ bne $9,$0,sctx ; yes - leave
+ add $8,$0,dskbase + dskbuf ; transfer data
+ add $9,$0,sctsize
+sctrd2:
+ ldw $10,$8,0 ; from disk buffer
+ stw $10,$18,0 ; to memory
+ add $8,$8,4
+ add $18,$18,4
+ sub $9,$9,4
+ bne $9,$0,sctrd2
+ add $17,$17,1 ; increment sector number
+ sub $19,$19,1 ; decrement number of sectors
+ j sctrd ; next sector
+
+sctwr:
+ add $2,$0,$0 ; return ok
+ beq $19,$0,sctx ; if no (more) sectors
+ add $8,$0,dskbase + dskbuf ; transfer data
+ add $9,$0,sctsize
+sctwr1:
+ ldw $10,$18,0 ; from memory
+ stw $10,$8,0 ; to disk buffer
+ add $18,$18,4
+ add $8,$8,4
+ sub $9,$9,4
+ bne $9,$0,sctwr1
+ add $8,$0,dskbase
+ add $9,$0,1
+ stw $9,$8,dskcnt ; number of sectors
+ stw $17,$8,dsksct ; sector number on disk
+ add $9,$0,ctrlwrt | ctrlstrt
+ stw $9,$8,dskctrl ; start command
+sctwr2:
+ ldw $2,$8,dskctrl
+ and $9,$2,ctrldone ; done?
+ beq $9,$0,sctwr2 ; no - wait
+ and $9,$2,ctrlerr ; error?
+ bne $9,$0,sctx ; yes - leave
+ add $17,$17,1 ; increment sector number
+ sub $19,$19,1 ; decrement number of sectors
+ j sctwr ; next sector
+
+sctx:
+ ldw $20,$29,0
+ ldw $19,$29,4
+ ldw $18,$29,8
+ ldw $17,$29,12
+ ldw $16,$29,16
+ ldw $31,$29,20
+ add $29,$29,24
+ jr $31
Index: monitor/monitor/command.h
===================================================================
--- monitor/monitor/command.h (nonexistent)
+++ monitor/monitor/command.h (revision 16)
@@ -0,0 +1,13 @@
+/*
+ * command.h -- command interpreter
+ */
+
+
+#ifndef _COMMAND_H_
+#define _COMMAND_H_
+
+
+void execCommand(char *line);
+
+
+#endif /* _COMMAND_H_ */
Index: monitor/monitor/main.c
===================================================================
--- monitor/monitor/main.c (nonexistent)
+++ monitor/monitor/main.c (revision 16)
@@ -0,0 +1,27 @@
+/*
+ * main.c -- the main program
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "command.h"
+#include "getline.h"
+#include "instr.h"
+#include "cpu.h"
+
+
+int main(void) {
+ char *line;
+
+ printf("\n\nECO32 Machine Monitor 1.0\n\n");
+ initInstrTable();
+ cpuSetPC(0xC0000000);
+ while (1) {
+ line = getLine("ECO32 > ");
+ addHist(line);
+ execCommand(line);
+ }
+ return 0;
+}
Index: monitor/monitor/romlib.c
===================================================================
--- monitor/monitor/romlib.c (nonexistent)
+++ monitor/monitor/romlib.c (revision 16)
@@ -0,0 +1,636 @@
+/*
+ * romlib.c -- the ROM library
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "start.h"
+
+
+/**************************************************************/
+
+
+/*
+ * This is only for debugging.
+ * Place a breakpoint at the very beginning of this routine
+ * and call it wherever you want to break execution.
+ */
+void debugBreak(void) {
+}
+
+
+/**************************************************************/
+
+
+/*
+ * Count the length of a string (without terminating null character).
+ */
+int strlen(const char *s) {
+ const char *p;
+
+ p = s;
+ while (*p != '\0') {
+ p++;
+ }
+ return p - s;
+}
+
+
+/*
+ * Compare two strings.
+ * Return a number < 0, = 0, or > 0 iff the first string is less
+ * than, equal to, or greater than the second one, respectively.
+ */
+int strcmp(const char *s, const char *t) {
+ while (*s == *t) {
+ if (*s == '\0') {
+ return 0;
+ }
+ s++;
+ t++;
+ }
+ return *s - *t;
+}
+
+
+/*
+ * Copy string t to string s (includes terminating null character).
+ */
+char *strcpy(char *s, const char *t) {
+ char *p;
+
+ p = s;
+ while ((*p = *t) != '\0') {
+ p++;
+ t++;
+ }
+ return s;
+}
+
+
+/*
+ * Append string t to string s.
+ */
+char *strcat(char *s, const char *t) {
+ char *p;
+
+ p = s;
+ while (*p != '\0') {
+ p++;
+ }
+ while ((*p = *t) != '\0') {
+ p++;
+ t++;
+ }
+ return s;
+}
+
+
+/*
+ * Locate character c in string s.
+ */
+char *strchr(const char *s, char c) {
+ while (*s != c) {
+ if (*s == '\0') {
+ return NULL;
+ }
+ s++;
+ }
+ return (char *) s;
+}
+
+
+/*
+ * Extract the next token from the string s, delimited
+ * by any character from the delimiter string t.
+ */
+char *strtok(char *s, const char *t) {
+ static char *p;
+ char *q;
+
+ if (s != NULL) {
+ p = s;
+ } else {
+ p++;
+ }
+ while (*p != '\0' && strchr(t, *p) != NULL) {
+ p++;
+ }
+ if (*p == '\0') {
+ return NULL;
+ }
+ q = p++;
+ while (*p != '\0' && strchr(t, *p) == NULL) {
+ p++;
+ }
+ if (*p != '\0') {
+ *p = '\0';
+ } else {
+ p--;
+ }
+ return q;
+}
+
+
+/**************************************************************/
+
+
+/*
+ * Determine if a character is 'white space'.
+ */
+static Bool isspace(char c) {
+ Bool res;
+
+ switch (c) {
+ case ' ':
+ case '\f':
+ case '\n':
+ case '\r':
+ case '\t':
+ case '\v':
+ res = true;
+ break;
+ default:
+ res = false;
+ break;
+ }
+ return res;
+}
+
+
+/*
+ * Check for valid digit, and convert to value.
+ */
+static Bool checkDigit(char c, int base, int *value) {
+ if (c >= '0' && c <= '9') {
+ *value = c - '0';
+ } else
+ if (c >= 'A' && c <= 'Z') {
+ *value = c - 'A' + 10;
+ } else
+ if (c >= 'a' && c <= 'z') {
+ *value = c - 'a' + 10;
+ } else {
+ return false;
+ }
+ return *value < base;
+}
+
+
+/*
+ * Convert initial part of string to unsigned long integer.
+ */
+unsigned long strtoul(const char *s, char **endp, int base) {
+ unsigned long res;
+ int sign;
+ int digit;
+
+ res = 0;
+ while (isspace(*s)) {
+ s++;
+ }
+ if (*s == '+') {
+ sign = 1;
+ s++;
+ } else
+ if (*s == '-') {
+ sign = -1;
+ s++;
+ } else {
+ sign = 1;
+ }
+ if (base == 0 || base == 16) {
+ if (*s == '0' &&
+ (*(s + 1) == 'x' || *(s + 1) == 'X')) {
+ /* base is 16 */
+ s += 2;
+ base = 16;
+ } else {
+ /* base is 0 or 16, but number does not start with "0x" */
+ if (base == 0) {
+ if (*s == '0') {
+ s++;
+ base = 8;
+ } else {
+ base = 10;
+ }
+ } else {
+ /* take base as is */
+ }
+ }
+ } else {
+ /* take base as is */
+ }
+ while (checkDigit(*s, base, &digit)) {
+ res *= base;
+ res += digit;
+ s++;
+ }
+ if (endp != NULL) {
+ *endp = (char *) s;
+ }
+ return sign * res;
+}
+
+
+/**************************************************************/
+
+
+/*
+ * Exchange two array items of a given size.
+ */
+static void xchg(char *p, char *q, int size) {
+ char t;
+
+ while (size--) {
+ t = *p;
+ *p++ = *q;
+ *q++ = t;
+ }
+}
+
+
+/*
+ * This is a recursive version of quicksort.
+ */
+static void sort(char *l, char *r, int size,
+ int (*cmp)(const void *, const void *)) {
+ char *i;
+ char *j;
+ char *x;
+
+ i = l;
+ j = r;
+ x = l + (((r - l) / size) / 2) * size;
+ do {
+ while (cmp(i, x) < 0) {
+ i += size;
+ }
+ while (cmp(x, j) < 0) {
+ j -= size;
+ }
+ if (i <= j) {
+ /* exchange array elements i and j */
+ /* attention: update x if it is one of these */
+ if (x == i) {
+ x = j;
+ } else
+ if (x == j) {
+ x = i;
+ }
+ xchg(i, j, size);
+ i += size;
+ j -= size;
+ }
+ } while (i <= j);
+ if (l < j) {
+ sort(l, j, size, cmp);
+ }
+ if (i < r) {
+ sort(i, r, size, cmp);
+ }
+}
+
+
+/*
+ * External interface for the quicksort algorithm.
+ */
+void qsort(void *base, int n, int size,
+ int (*cmp)(const void *, const void*)) {
+ sort((char *) base, (char *) base + (n - 1) * size, size, cmp);
+}
+
+
+/**************************************************************/
+
+
+/*
+ * Input a character from the console.
+ */
+char getchar(void) {
+ return cin();
+}
+
+
+/*
+ * Output a character on the console.
+ * Replace LF by CR/LF.
+ */
+void putchar(char c) {
+ if (c == '\n') {
+ cout('\r');
+ }
+ cout(c);
+}
+
+
+/*
+ * Output a string on the console.
+ * Replace LF by CR/LF.
+ */
+void puts(const char *s) {
+ while (*s != '\0') {
+ putchar(*s);
+ s++;
+ }
+}
+
+
+/**************************************************************/
+
+
+/*
+ * Count the number of characters needed to represent
+ * a given number in base 10.
+ */
+static int countPrintn(long n) {
+ long a;
+ int res;
+
+ res = 0;
+ if (n < 0) {
+ res++;
+ n = -n;
+ }
+ a = n / 10;
+ if (a != 0) {
+ res += countPrintn(a);
+ }
+ return res + 1;
+}
+
+
+/*
+ * Output a number in base 10.
+ */
+static void *printn(void *(*emit)(void *, char), void *arg,
+ int *nchar, long n) {
+ long a;
+
+ if (n < 0) {
+ arg = emit(arg, '-');
+ (*nchar)++;
+ n = -n;
+ }
+ a = n / 10;
+ if (a != 0) {
+ arg = printn(emit, arg, nchar, a);
+ }
+ arg = emit(arg, n % 10 + '0');
+ (*nchar)++;
+ return arg;
+}
+
+
+/*
+ * Count the number of characters needed to represent
+ * a given number in a given base.
+ */
+static int countPrintu(unsigned long n, unsigned long b) {
+ unsigned long a;
+ int res;
+
+ res = 0;
+ a = n / b;
+ if (a != 0) {
+ res += countPrintu(a, b);
+ }
+ return res + 1;
+}
+
+
+/*
+ * Output a number in a given base.
+ */
+static void *printu(void *(*emit)(void *, char), void *arg,
+ int *nchar, unsigned long n, unsigned long b,
+ Bool upperCase) {
+ unsigned long a;
+
+ a = n / b;
+ if (a != 0) {
+ arg = printu(emit, arg, nchar, a, b, upperCase);
+ }
+ if (upperCase) {
+ arg = emit(arg, "0123456789ABCDEF"[n % b]);
+ (*nchar)++;
+ } else {
+ arg = emit(arg, "0123456789abcdef"[n % b]);
+ (*nchar)++;
+ }
+ return arg;
+}
+
+
+/*
+ * Output a number of filler characters.
+ */
+static void *fill(void *(*emit)(void *, char), void *arg,
+ int *nchar, int numFillers, char filler) {
+ while (numFillers-- > 0) {
+ arg = emit(arg, filler);
+ (*nchar)++;
+ }
+ return arg;
+}
+
+
+/*
+ * This function does the real work of formatted printing.
+ */
+static int doPrintf(void *(*emit)(void *, char), void *arg,
+ const char *fmt, va_list ap) {
+ int nchar;
+ char c;
+ int n;
+ long ln;
+ unsigned int u;
+ unsigned long lu;
+ char *s;
+ Bool negFlag;
+ char filler;
+ int width, count;
+
+ nchar = 0;
+ while (1) {
+ while ((c = *fmt++) != '%') {
+ if (c == '\0') {
+ return nchar;
+ }
+ arg = emit(arg, c);
+ nchar++;
+ }
+ c = *fmt++;
+ if (c == '-') {
+ negFlag = true;
+ c = *fmt++;
+ } else {
+ negFlag = false;
+ }
+ if (c == '0') {
+ filler = '0';
+ c = *fmt++;
+ } else {
+ filler = ' ';
+ }
+ width = 0;
+ while (c >= '0' && c <= '9') {
+ width *= 10;
+ width += c - '0';
+ c = *fmt++;
+ }
+ if (c == 'd') {
+ n = va_arg(ap, int);
+ count = countPrintn(n);
+ if (width > 0 && !negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ arg = printn(emit, arg, &nchar, n);
+ if (width > 0 && negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ } else
+ if (c == 'u' || c == 'o' || c == 'x' || c == 'X') {
+ u = va_arg(ap, int);
+ count = countPrintu(u,
+ c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10));
+ if (width > 0 && !negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ arg = printu(emit, arg, &nchar, u,
+ c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10),
+ c == 'X');
+ if (width > 0 && negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ } else
+ if (c == 'l') {
+ c = *fmt++;
+ if (c == 'd') {
+ ln = va_arg(ap, long);
+ count = countPrintn(ln);
+ if (width > 0 && !negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ arg = printn(emit, arg, &nchar, ln);
+ if (width > 0 && negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ } else
+ if (c == 'u' || c == 'o' || c == 'x' || c == 'X') {
+ lu = va_arg(ap, long);
+ count = countPrintu(lu,
+ c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10));
+ if (width > 0 && !negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ arg = printu(emit, arg, &nchar, lu,
+ c == 'o' ? 8 : ((c == 'x' || c == 'X') ? 16 : 10),
+ c == 'X');
+ if (width > 0 && negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ } else {
+ arg = emit(arg, 'l');
+ nchar++;
+ arg = emit(arg, c);
+ nchar++;
+ }
+ } else
+ if (c == 's') {
+ s = va_arg(ap, char *);
+ count = strlen(s);
+ if (width > 0 && !negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ while ((c = *s++) != '\0') {
+ arg = emit(arg, c);
+ nchar++;
+ }
+ if (width > 0 && negFlag) {
+ arg = fill(emit, arg, &nchar, width - count, filler);
+ }
+ } else
+ if (c == 'c') {
+ c = va_arg(ap, char);
+ arg = emit(arg, c);
+ nchar++;
+ } else {
+ arg = emit(arg, c);
+ nchar++;
+ }
+ }
+ /* never reached */
+ return 0;
+}
+
+
+/*
+ * Emit a character to the console.
+ */
+static void *emitToConsole(void *dummy, char c) {
+ putchar(c);
+ return dummy;
+}
+
+
+/*
+ * Formatted output with a variable argument list.
+ */
+int vprintf(const char *fmt, va_list ap) {
+ int n;
+
+ n = doPrintf(emitToConsole, NULL, fmt, ap);
+ return n;
+}
+
+
+/*
+ * Formatted output.
+ */
+int printf(const char *fmt, ...) {
+ int n;
+ va_list ap;
+
+ va_start(ap, fmt);
+ n = vprintf(fmt, ap);
+ va_end(ap);
+ return n;
+}
+
+
+/*
+ * Emit a character to a buffer.
+ */
+static void *emitToBuffer(void *bufptr, char c) {
+ *(char *)bufptr = c;
+ return (char *) bufptr + 1;
+}
+
+
+/*
+ * Formatted output into a buffer with a variable argument list.
+ */
+int vsprintf(char *s, const char *fmt, va_list ap) {
+ int n;
+
+ n = doPrintf(emitToBuffer, s, fmt, ap);
+ s[n] = '\0';
+ return n;
+}
+
+
+/*
+ * Formatted output into a buffer.
+ */
+int sprintf(char *s, const char *fmt, ...) {
+ int n;
+ va_list ap;
+
+ va_start(ap, fmt);
+ n = vsprintf(s, fmt, ap);
+ va_end(ap);
+ return n;
+}
Index: monitor/monitor/display.s
===================================================================
--- monitor/monitor/display.s (nonexistent)
+++ monitor/monitor/display.s (revision 16)
@@ -0,0 +1,225 @@
+;
+; display.s -- a memory-mapped alphanumerical display
+;
+
+;***************************************************************
+
+ .set dspbase,0xF0100000 ; display base address
+
+ .export dspinit ; initialize display
+ .export dspoutchk ; check for output possible
+ .export dspout ; do display output
+
+;***************************************************************
+
+ .code
+ .align 4
+
+ ; initialize display
+dspinit:
+ sub $29,$29,4
+ stw $31,$29,0
+ jal clrscr
+ add $8,$0,scrrow
+ stw $0,$8,0
+ add $8,$0,scrcol
+ stw $0,$8,0
+ jal calcp
+ jal stcrs
+ ldw $31,$29,0
+ add $29,$29,4
+ jr $31
+
+ ; check if a character can be written
+dspoutchk:
+ add $2,$0,1
+ jr $31
+
+ ; output a character on the display
+dspout:
+ sub $29,$29,8
+ stw $31,$29,4
+ stw $16,$29,0
+ and $16,$4,0xFF
+ jal rmcrs
+ add $8,$0,' '
+ bltu $16,$8,dspout2
+ add $8,$0,scrptr
+ ldw $9,$8,0
+ or $16,$16,0x07 << 8
+ stw $16,$9,0
+ add $9,$9,4
+ stw $9,$8,0
+ add $8,$0,scrcol
+ ldw $9,$8,0
+ add $9,$9,1
+ stw $9,$8,0
+ add $10,$0,80
+ bne $9,$10,dspout1
+ jal docr
+ jal dolf
+dspout1:
+ jal stcrs
+ ldw $16,$29,0
+ ldw $31,$29,4
+ add $29,$29,8
+ jr $31
+
+dspout2:
+ add $8,$0,0x0D
+ bne $16,$8,dspout3
+ jal docr
+ j dspout1
+
+dspout3:
+ add $8,$0,0x0A
+ bne $16,$8,dspout4
+ jal dolf
+ j dspout1
+
+dspout4:
+ add $8,$0,0x08
+ bne $16,$8,dspout5
+ jal dobs
+ j dspout1
+
+dspout5:
+ j dspout1
+
+ ; do carriage return
+docr:
+ sub $29,$29,4
+ stw $31,$29,0
+ add $8,$0,scrcol
+ stw $0,$8,0
+ jal calcp
+ ldw $31,$29,0
+ add $29,$29,4
+ jr $31
+
+ ; do linefeed
+dolf:
+ sub $29,$29,4
+ stw $31,$29,0
+ add $8,$0,scrrow
+ ldw $9,$8,0
+ add $10,$0,29
+ beq $9,$10,dolf1
+ add $9,$9,1
+ stw $9,$8,0
+ jal calcp
+ j dolf2
+dolf1:
+ jal scrscr
+dolf2:
+ ldw $31,$29,0
+ add $29,$29,4
+ jr $31
+
+ ; do backspace
+dobs:
+ sub $29,$29,4
+ stw $31,$29,0
+ add $8,$0,scrcol
+ ldw $9,$8,0
+ beq $9,$0,dobs1
+ sub $9,$9,1
+ stw $9,$8,0
+ jal calcp
+dobs1:
+ ldw $31,$29,0
+ add $29,$29,4
+ jr $31
+
+ ; remove cursor
+rmcrs:
+ add $8,$0,scrptr
+ ldw $8,$8,0
+ add $9,$0,scrchr
+ ldw $10,$9,0
+ stw $10,$8,0
+ jr $31
+
+ ; set cursor
+stcrs:
+ add $8,$0,scrptr
+ ldw $8,$8,0
+ add $9,$0,scrchr
+ ldw $10,$8,0
+ stw $10,$9,0
+ add $10,$0,(0x87 << 8) | '_'
+ stw $10,$8,0
+ jr $31
+
+ ; calculate screen pointer based on row and column
+calcp:
+ add $9,$0,dspbase
+ add $8,$0,scrrow
+ ldw $10,$8,0
+ sll $10,$10,7+2
+ add $9,$9,$10
+ add $8,$0,scrcol
+ ldw $10,$8,0
+ sll $10,$10,0+2
+ add $9,$9,$10
+ add $8,$0,scrptr
+ stw $9,$8,0
+ jr $31
+
+ ; clear screen
+clrscr:
+ add $11,$0,(0x07 << 8) | ' '
+ add $8,$0,dspbase
+ add $9,$0,30
+clrscr1:
+ add $10,$0,80
+clrscr2:
+ stw $11,$8,0
+ add $8,$8,4
+ sub $10,$10,1
+ bne $10,$0,clrscr2
+ add $8,$8,(128-80)*4
+ sub $9,$9,1
+ bne $9,$0,clrscr1
+ jr $31
+
+ ; scroll screen
+scrscr:
+ add $8,$0,dspbase
+ add $9,$0,29
+scrscr1:
+ add $10,$0,80
+scrscr2:
+ ldw $11,$8,128*4
+ stw $11,$8,0
+ add $8,$8,4
+ sub $10,$10,1
+ bne $10,$0,scrscr2
+ add $8,$8,(128-80)*4
+ sub $9,$9,1
+ bne $9,$0,scrscr1
+ add $11,$0,(0x07 << 8) | ' '
+ add $10,$0,80
+scrscr3:
+ stw $11,$8,0
+ add $8,$8,4
+ sub $10,$10,1
+ bne $10,$0,scrscr3
+ jr $31
+
+;***************************************************************
+
+ .bss
+ .align 4
+
+scrptr:
+ .word 0
+
+scrrow:
+ .word 0
+
+scrcol:
+ .word 0
+
+scrchr:
+ .word 0
Index: monitor/monitor/disasm.h
===================================================================
--- monitor/monitor/disasm.h (nonexistent)
+++ monitor/monitor/disasm.h (revision 16)
@@ -0,0 +1,13 @@
+/*
+ * disasm.h -- disassembler
+ */
+
+
+#ifndef _DISASM_H_
+#define _DISASM_H_
+
+
+char *disasm(Word instr, Word locus);
+
+
+#endif /* _DISASM_H_ */
Index: monitor/monitor/asm.h
===================================================================
--- monitor/monitor/asm.h (nonexistent)
+++ monitor/monitor/asm.h (revision 16)
@@ -0,0 +1,13 @@
+/*
+ * asm.h -- assembler
+ */
+
+
+#ifndef _ASM_H_
+#define _ASM_H_
+
+
+char *asmInstr(char *line, Word addr, Word *instrPtr);
+
+
+#endif /* _ASM_H_ */
Index: monitor/monitor/end.s
===================================================================
--- monitor/monitor/end.s (nonexistent)
+++ monitor/monitor/end.s (revision 16)
@@ -0,0 +1,19 @@
+;
+; end.s -- end-of-segment labels
+;
+
+ .export _ecode
+ .export _edata
+ .export _ebss
+
+ .code
+ .align 4
+_ecode:
+
+ .data
+ .align 4
+_edata:
+
+ .bss
+ .align 4
+_ebss:
Index: monitor/monitor/getline.c
===================================================================
--- monitor/monitor/getline.c (nonexistent)
+++ monitor/monitor/getline.c (revision 16)
@@ -0,0 +1,136 @@
+/*
+ * getline.c -- line input
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "getline.h"
+
+
+#define MAX_HISTORY 100
+
+
+static char history[MAX_HISTORY][80];
+static int historyIndex; /* next line to be written */
+
+
+/*
+ * Get a line from the console.
+ */
+char *getLine(char *prompt) {
+ static char line[80];
+ int index;
+ int historyPointer;
+ char c;
+ int i;
+
+ printf(prompt);
+ index = 0;
+ historyPointer = historyIndex;
+ while (1) {
+ c = getchar();
+ switch (c) {
+ case '\r':
+ putchar('\n');
+ line[index] = '\0';
+ return line;
+ case '\b':
+ case 0x7F:
+ if (index == 0) {
+ break;
+ }
+ putchar('\b');
+ putchar(' ');
+ putchar('\b');
+ index--;
+ break;
+ case 'P' & ~0x40:
+ if (historyPointer == historyIndex) {
+ line[index] = '\0';
+ strcpy(history[historyIndex], line);
+ }
+ i = historyPointer - 1;
+ if (i == -1) {
+ i = MAX_HISTORY - 1;
+ }
+ if (i == historyIndex) {
+ putchar('\a');
+ break;
+ }
+ if (history[i][0] == '\0') {
+ putchar('\a');
+ break;
+ }
+ historyPointer = i;
+ strcpy(line, history[historyPointer]);
+ printf("\r");
+ for (i = 0; i < 79; i++) {
+ printf(" ");
+ }
+ printf("\r");
+ printf(prompt);
+ printf(line);
+ index = strlen(line);
+ break;
+ case 'N' & ~0x40:
+ if (historyPointer == historyIndex) {
+ putchar('\a');
+ break;
+ }
+ i = historyPointer + 1;
+ if (i == MAX_HISTORY) {
+ i = 0;
+ }
+ historyPointer = i;
+ strcpy(line, history[historyPointer]);
+ printf("\r");
+ for (i = 0; i < 79; i++) {
+ printf(" ");
+ }
+ printf("\r");
+ printf(prompt);
+ printf(line);
+ index = strlen(line);
+ break;
+ default:
+ if (c == '\t') {
+ c = ' ';
+ }
+ if (c < 0x20 || c > 0x7E) {
+ break;
+ }
+ putchar(c);
+ line[index++] = c;
+ break;
+ }
+ }
+ /* never reached */
+ return NULL;
+}
+
+
+/*
+ * Add a line to the history.
+ * Don't do this if the line is empty, or if its
+ * contents exactly match the previous line.
+ */
+void addHist(char *line) {
+ int lastWritten;
+
+ if (*line == '\0') {
+ return;
+ }
+ lastWritten = historyIndex - 1;
+ if (lastWritten == -1) {
+ lastWritten = MAX_HISTORY - 1;
+ }
+ if (strcmp(history[lastWritten], line) == 0) {
+ return;
+ }
+ strcpy(history[historyIndex], line);
+ if (++historyIndex == MAX_HISTORY) {
+ historyIndex = 0;
+ }
+}
Index: monitor/monitor/cpu.c
===================================================================
--- monitor/monitor/cpu.c (nonexistent)
+++ monitor/monitor/cpu.c (revision 16)
@@ -0,0 +1,367 @@
+/*
+ * cpu.c -- execute instructions
+ */
+
+
+#include "common.h"
+#include "stdarg.h"
+#include "romlib.h"
+#include "instr.h"
+#include "cpu.h"
+#include "mmu.h"
+#include "start.h"
+
+
+#define RR(n) r[n]
+#define WR(n,d) ((void) ((n) != 0 ? r[n] = (d) : (d)))
+
+#define BREAK (OP_TRAP << 26)
+
+
+/**************************************************************/
+
+
+static Word pc; /* program counter */
+static Word psw; /* processor status word */
+static Word r[32]; /* general purpose registers */
+
+static Bool breakSet; /* breakpoint set if true */
+static Word breakAddr; /* if breakSet, this is where */
+
+
+/**************************************************************/
+
+
+Word cpuGetPC(void) {
+ return pc;
+}
+
+
+void cpuSetPC(Word addr) {
+ pc = addr;
+}
+
+
+Word cpuGetReg(int regnum) {
+ return RR(regnum & 0x1F);
+}
+
+
+void cpuSetReg(int regnum, Word value) {
+ WR(regnum & 0x1F, value);
+}
+
+
+Word cpuGetPSW(void) {
+ return psw;
+}
+
+
+void cpuSetPSW(Word value) {
+ psw = value;
+}
+
+
+Bool cpuTestBreak(void) {
+ return breakSet;
+}
+
+
+Word cpuGetBreak(void) {
+ return breakAddr;
+}
+
+
+void cpuSetBreak(Word addr) {
+ breakAddr = addr;
+ breakSet = true;
+}
+
+
+void cpuResetBreak(void) {
+ breakSet = false;
+}
+
+
+/**************************************************************/
+
+
+static char *cause[32] = {
+ /* 0 */ "terminal 0 transmitter interrupt",
+ /* 1 */ "terminal 0 receiver interrupt",
+ /* 2 */ "terminal 1 transmitter interrupt",
+ /* 3 */ "terminal 1 receiver interrupt",
+ /* 4 */ "keyboard interrupt",
+ /* 5 */ "unknown interrupt",
+ /* 6 */ "unknown interrupt",
+ /* 7 */ "unknown interrupt",
+ /* 8 */ "disk interrupt",
+ /* 9 */ "unknown interrupt",
+ /* 10 */ "unknown interrupt",
+ /* 11 */ "unknown interrupt",
+ /* 12 */ "unknown interrupt",
+ /* 13 */ "unknown interrupt",
+ /* 14 */ "timer interrupt",
+ /* 15 */ "unknown interrupt",
+ /* 16 */ "bus timeout exception",
+ /* 17 */ "illegal instruction exception",
+ /* 18 */ "privileged instruction exception",
+ /* 19 */ "divide instruction exception",
+ /* 20 */ "trap instruction exception",
+ /* 21 */ "TLB miss exception",
+ /* 22 */ "TLB write exception",
+ /* 23 */ "TLB invalid exception",
+ /* 24 */ "illegal address exception",
+ /* 25 */ "privileged address exception",
+ /* 26 */ "unknown exception",
+ /* 27 */ "unknown exception",
+ /* 28 */ "unknown exception",
+ /* 29 */ "unknown exception",
+ /* 30 */ "unknown exception",
+ /* 31 */ "unknown exception"
+};
+
+
+char *exceptionToString(int exception) {
+ if (exception < 0 ||
+ exception >= sizeof(cause)/sizeof(cause[0])) {
+ return "";
+ }
+ return cause[exception];
+}
+
+
+/**************************************************************/
+
+
+static Byte stepType[64] = {
+ /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */
+ /* 0x00 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ /* 0x10 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+ /* 0x20 */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 4, 3, 4, 1, 0,
+ /* 0x30 */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
+};
+
+
+static Bool evalCond(int cc, Word a, Word b) {
+ switch (cc) {
+ case 0:
+ /* equal */
+ if (a == b) {
+ return true;
+ }
+ break;
+ case 1:
+ /* not equal */
+ if (a != b) {
+ return true;
+ }
+ break;
+ case 2:
+ /* less or equal (signed) */
+ if ((signed int) a <= (signed int) b) {
+ return true;
+ }
+ break;
+ case 3:
+ /* less or equal (unsigned) */
+ if (a <= b) {
+ return true;
+ }
+ break;
+ case 4:
+ /* less than (signed) */
+ if ((signed int) a < (signed int) b) {
+ return true;
+ }
+ break;
+ case 5:
+ /* less than (unsigned) */
+ if (a < b) {
+ return true;
+ }
+ break;
+ case 6:
+ /* greater or equal (signed) */
+ if ((signed int) a >= (signed int) b) {
+ return true;
+ }
+ break;
+ case 7:
+ /* greater or equal (unsigned) */
+ if (a >= b) {
+ return true;
+ }
+ break;
+ case 8:
+ /* greater than (signed) */
+ if ((signed int) a > (signed int) b) {
+ return true;
+ }
+ break;
+ case 9:
+ /* greater than (unsigned) */
+ if (a > b) {
+ return true;
+ }
+ break;
+ default:
+ printf("cannot compute condition code %d\n", cc);
+ break;
+ }
+ return false;
+}
+
+
+Bool cpuStep(void) {
+ Word instr;
+ int opcode;
+ int reg1, reg2;
+ Half immed;
+ Word offset;
+ Bool canStep;
+ Word nextAddr;
+ Word nextInstr;
+ int i;
+ MonitorState stepState;
+ MonitorState *origReturn;
+
+ instr = mmuReadWord(pc);
+ opcode = (instr >> 26) & 0x3F;
+ reg1 = (instr >> 21) & 0x1F;
+ reg2 = (instr >> 16) & 0x1F;
+ immed = instr & 0x0000FFFF;
+ offset = instr & 0x03FFFFFF;
+ canStep = true;
+ switch (stepType[opcode]) {
+ case 1:
+ /* next instruction follows current one */
+ nextAddr = pc + 4;
+ break;
+ case 2:
+ /* next instruction conditionally reached by PC relative branch */
+ nextAddr = pc + 4;
+ if (evalCond(opcode - OP_BEQ, RR(reg1), RR(reg2))) {
+ nextAddr += SEXT16(immed) << 2;
+ }
+ break;
+ case 3:
+ /* next instruction reached by PC relative jump */
+ nextAddr = pc + 4 + (SEXT26(offset) << 2);
+ break;
+ case 4:
+ /* next instruction reached by jump to register contents */
+ nextAddr = RR(reg1);
+ break;
+ default:
+ printf("cannot single-step instruction with opcode 0x%02X\n",
+ opcode);
+ canStep = false;
+ break;
+ }
+ if (!canStep) {
+ return false;
+ }
+ nextInstr = mmuReadWord(nextAddr);
+ mmuWriteWord(nextAddr, BREAK);
+ for (i = 0; i < 32; i++) {
+ userContext.reg[i] = RR(i);
+ }
+ userContext.reg[30] = pc;
+ userContext.psw = psw & ~PSW_V;
+ userContext.tlbIndex = mmuGetIndex();
+ userContext.tlbHi = mmuGetEntryHi();
+ userContext.tlbLo = mmuGetEntryLo();
+ if (saveState(&stepState)) {
+ origReturn = monitorReturn;
+ monitorReturn = &stepState;
+ resume();
+ }
+ monitorReturn = origReturn;
+ for (i = 0; i < 32; i++) {
+ WR(i, userContext.reg[i]);
+ }
+ pc = userContext.reg[30];
+ psw = userContext.psw | (psw & PSW_V);
+ mmuSetIndex(userContext.tlbIndex);
+ mmuSetEntryHi(userContext.tlbHi);
+ mmuSetEntryLo(userContext.tlbLo);
+ mmuWriteWord(nextAddr, nextInstr);
+ if (nextAddr == pc) {
+ return true;
+ }
+ if ((psw & PSW_V) == 0) {
+ printf("unexpected %s occurred\n",
+ exceptionToString((psw & PSW_PRIO_MASK) >> 16));
+ return false;
+ }
+ if ((psw & PSW_PRIO_MASK) >> 16 == 21 &&
+ (mmuGetEntryHi() & 0x80000000) == 0) {
+ pc = 0xC0000008;
+ } else {
+ pc = 0xC0000004;
+ }
+ return true;
+}
+
+
+Bool cpuRun(void) {
+ Word instr;
+ int i;
+ MonitorState runState;
+ MonitorState *origReturn;
+
+ if (breakSet && breakAddr == pc) {
+ /* single-step one instruction */
+ if (!cpuStep()) {
+ return false;
+ }
+ }
+ while (1) {
+ if (breakSet) {
+ instr = mmuReadWord(breakAddr);
+ mmuWriteWord(breakAddr, BREAK);
+ }
+ for (i = 0; i < 32; i++) {
+ userContext.reg[i] = RR(i);
+ }
+ userContext.reg[30] = pc;
+ userContext.psw = psw & ~PSW_V;
+ userContext.tlbIndex = mmuGetIndex();
+ userContext.tlbHi = mmuGetEntryHi();
+ userContext.tlbLo = mmuGetEntryLo();
+ if (saveState(&runState)) {
+ origReturn = monitorReturn;
+ monitorReturn = &runState;
+ resume();
+ }
+ monitorReturn = origReturn;
+ for (i = 0; i < 32; i++) {
+ WR(i, userContext.reg[i]);
+ }
+ pc = userContext.reg[30];
+ psw = userContext.psw | (psw & PSW_V);
+ mmuSetIndex(userContext.tlbIndex);
+ mmuSetEntryHi(userContext.tlbHi);
+ mmuSetEntryLo(userContext.tlbLo);
+ if (breakSet) {
+ mmuWriteWord(breakAddr, instr);
+ }
+ if (breakSet && breakAddr == pc) {
+ return true;
+ }
+ if ((psw & PSW_V) == 0) {
+ printf("unexpected %s occurred\n",
+ exceptionToString((psw & PSW_PRIO_MASK) >> 16));
+ return false;
+ }
+ if ((psw & PSW_PRIO_MASK) >> 16 == 21 &&
+ (mmuGetEntryHi() & 0x80000000) == 0) {
+ pc = 0xC0000008;
+ } else {
+ pc = 0xC0000004;
+ }
+ }
+ /* never reached */
+ return false;
+}
Index: monitor/monitor/sctio-ser.s
===================================================================
--- monitor/monitor/sctio-ser.s (nonexistent)
+++ monitor/monitor/sctio-ser.s (revision 16)
@@ -0,0 +1,200 @@
+;
+; sctio-ser.s -- disk sector I/O for disk made available by serial interface
+;
+
+;***************************************************************
+
+ .export sctcapser ; determine disk capacity
+ .export sctioser ; do disk I/O
+
+ .import ser1in
+ .import ser1out
+ .import ser1inchk
+ .import puts
+
+ ; constants for communication with disk server
+ .set SYN,0x16 ; to initiate the three-way handshake
+ .set ACK,0x06 ; acknowledgement for handshake
+ .set RESULT_OK,0x00 ; server successfully executed cmd
+ ; everything else means error
+
+ .set WAIT_DELAY,800000 ; count for delay loop
+
+;***************************************************************
+
+ .code
+ .align 4
+
+sctcapser:
+ sub $29,$29,16
+ stw $16,$29,0
+ stw $17,$29,4
+ stw $18,$29,8
+ stw $31,$29,12
+ add $4,$0,trymsg ; say what we are doing
+ jal puts
+ add $18,$0,$0 ; capacity == 0 if disk not present
+ add $16,$0,10 ; 10 tries to get a connection
+handshake1:
+ sub $16,$16,1
+ add $4,$0,SYN
+ jal ser1out ; send SYN
+ add $17,$0,WAIT_DELAY ; wait for ACK
+handshake2:
+ sub $17,$17,1
+ jal ser1inchk
+ bne $2,$0,handshake3
+ bne $17,$0,handshake2
+ add $4,$0,timeoutmsg
+ jal puts
+ bne $16,$0,handshake1
+ add $4,$0,frustratedmsg
+ jal puts
+ j sctcapx
+handshake3:
+ jal ser1in
+ add $8,$0,ACK
+ bne $2,$8,sctcapx
+ ; we got an ACK so we return it
+ add $4,$0,ACK
+ jal ser1out
+
+ ; ask it for its capacity
+ add $4,$0,'c'
+ jal ser1out ; request
+ jal ser1in ; first byte of response
+ bne $2,$0,sctcapx ; exit if error
+
+ ; all is well and the server will give us the capacity
+ add $16,$0,4 ; 4 bytes to read
+sctcap1:
+ sll $18,$18,8
+ jal ser1in
+ or $18,$18,$2 ; most significant byte first
+ sub $16,$16,1
+ bne $16,$0,sctcap1
+
+ ; return value is in $18
+sctcapx:
+ add $2,$0,$18
+ ldw $16,$29,0
+ ldw $17,$29,4
+ ldw $18,$29,8
+ ldw $31,$29,12
+ add $29,$29,16
+ jr $31
+
+ .data
+ .align 4
+
+trymsg:
+ .byte "Trying to connect to disk server..."
+ .byte 0x0A, 0
+
+timeoutmsg:
+ .byte "Request timed out..."
+ .byte 0x0A, 0
+
+frustratedmsg:
+ .byte "Unable to establish connection to disk server."
+ .byte 0x0A, 0
+
+ .code
+ .align 4
+
+sctioser:
+ sub $29,$29,24
+ stw $16,$29,0
+ stw $17,$29,4
+ stw $18,$29,8
+ stw $19,$29,12
+ stw $20,$29,16
+ stw $31,$29,20
+ add $16,$0,$4 ; command
+ add $17,$0,$5 ; start at sector
+ add $8,$0,0xc0000000
+ or $18,$8,$6 ; memory address (logicalized)
+ add $19,$0,$7 ; number of sectors
+
+ ; switch over command
+ add $8,$0,'r'
+ beq $8,$16,sctior ; read
+ add $8,$0,'w'
+ beq $8,$16,sctiow ; write
+ ; unknown command
+ add $2,$0,1 ; value != 0 signifies error
+ j sctiox
+
+ ; read from disk
+sctior:
+sctior1: ; loop over number of sectors
+ beq $19,$0,sctiorsuc ; successful return
+ sub $19,$19,1
+ ; read a sector
+ add $4,$0,'r'
+ jal ser1out
+ ; send sector number
+ add $20,$0,32 ; 4 bytes
+sctior2:
+ sub $20,$20,8
+ slr $4,$17,$20
+ and $4,$4,0xff
+ jal ser1out
+ bne $20,$0,sctior2
+ add $17,$17,1
+ ; get answer
+ jal ser1in
+ bne $2,$0,sctiox ; $2 != 0 so we use it as return code
+ ; read data
+ add $20,$0,512
+sctior3:
+ sub $20,$20,1
+ jal ser1in
+ stb $2,$18,0
+ add $18,$18,1
+ bne $20,$0,sctior3
+ j sctior1
+sctiorsuc:
+ add $2,$0,$0
+ j sctiox
+
+ ; write to disk
+sctiow:
+sctiow1: ; loop over number of sectors
+ beq $19,$0,sctiowsuc ; successful return
+ sub $19,$19,1
+ ; write a sector
+ add $4,$0,'w'
+ jal ser1out
+ ; send sector number
+ add $20,$0,32 ; 4 bytes
+sctiow2:
+ sub $20,$20,8
+ slr $4,$17,$20
+ and $4,$4,0xff
+ jal ser1out
+ bne $20,$0,sctiow2
+ add $17,$17,1
+ ; write data
+ add $20,$0,512
+sctiow3:
+ sub $20,$20,1
+ ldbu $4,$18,0
+ jal ser1out
+ add $18,$18,1
+ bne $20,$0,sctiow3
+ ; get answer
+ jal ser1in
+ bne $2,$0,sctiox
+ j sctiow1
+sctiowsuc:
+ add $2,$0,$0
+sctiox:
+ ldw $16,$29,0
+ ldw $17,$29,4
+ ldw $18,$29,8
+ ldw $19,$29,12
+ ldw $20,$29,16
+ ldw $31,$29,20
+ add $29,$29,24
+ jr $31
Index: monitor/monitor/stdarg.h
===================================================================
--- monitor/monitor/stdarg.h (nonexistent)
+++ monitor/monitor/stdarg.h (revision 16)
@@ -0,0 +1,41 @@
+/*
+ * stdarg.h -- variable argument lists
+ */
+
+
+#ifndef _STDARG_H_
+#define _STDARG_H_
+
+
+typedef char *va_list;
+
+
+static float __va_arg_tmp;
+
+
+#define va_start(list, start) \
+ ((void)((list) = (sizeof(start)<4 ? \
+ (char *)((int *)&(start)+1) : (char *)(&(start)+1))))
+
+#define __va_arg(list, mode, n) \
+ (__typecode(mode)==1 && sizeof(mode)==4 ? \
+ (__va_arg_tmp = *(double *)(&(list += \
+ ((sizeof(double)+n)&~n))[-(int)((sizeof(double)+n)&~n)]), \
+ *(mode *)&__va_arg_tmp) : \
+ *(mode *)(&(list += \
+ ((sizeof(mode)+n)&~n))[-(int)((sizeof(mode)+n)&~n)]))
+
+#define _bigendian_va_arg(list, mode, n) \
+ (sizeof(mode)==1 ? *(mode *)(&(list += 4)[-1]) : \
+ sizeof(mode)==2 ? *(mode *)(&(list += 4)[-2]) : \
+ __va_arg(list, mode, n))
+
+#define va_end(list) ((void)0)
+
+#define va_arg(list, mode) \
+ (sizeof(mode)==8 ? \
+ *(mode *)(&(list = (char*)(((int)list + 15)&~7U))[-8]) : \
+ _bigendian_va_arg(list, mode, 3U))
+
+
+#endif /* _STDARG_H_ */
Index: monitor/monitor/romlib.h
===================================================================
--- monitor/monitor/romlib.h (nonexistent)
+++ monitor/monitor/romlib.h (revision 16)
@@ -0,0 +1,34 @@
+/*
+ * romlib.h -- the ROM library
+ */
+
+
+#ifndef _ROMLIB_H_
+#define _ROMLIB_H_
+
+
+void debugBreak(void);
+
+int strlen(const char *s);
+int strcmp(const char *s, const char *t);
+char *strcpy(char *s, const char *t);
+char *strcat(char *s, const char *t);
+char *strchr(const char *s, char c);
+char *strtok(char *s, const char *t);
+
+unsigned long strtoul(const char *s, char **endp, int base);
+
+void qsort(void *base, int n, int size,
+ int (*cmp)(const void *, const void *));
+
+char getchar(void);
+void putchar(char c);
+void puts(const char *s);
+
+int vprintf(const char *fmt, va_list ap);
+int printf(const char *fmt, ...);
+int vsprintf(char *s, const char *fmt, va_list ap);
+int sprintf(char *s, const char *fmt, ...);
+
+
+#endif /* _ROMLIB_H_ */
Index: monitor/monitor/getline.h
===================================================================
--- monitor/monitor/getline.h (nonexistent)
+++ monitor/monitor/getline.h (revision 16)
@@ -0,0 +1,14 @@
+/*
+ * getline.h -- line input
+ */
+
+
+#ifndef _GETLINE_H_
+#define _GETLINE_H_
+
+
+char *getLine(char *prompt);
+void addHist(char *line);
+
+
+#endif /* _GETLINE_H_ */
Index: monitor/monitor/cpu.h
===================================================================
--- monitor/monitor/cpu.h (nonexistent)
+++ monitor/monitor/cpu.h (revision 16)
@@ -0,0 +1,40 @@
+/*
+ * cpu.h -- execute instructions
+ */
+
+
+#ifndef _CPU_H_
+#define _CPU_H_
+
+
+#define PSW_V 0x08000000 /* interrupt vector bit in PSW */
+#define PSW_UM 0x04000000 /* user mode enable bit in PSW */
+#define PSW_PUM 0x02000000 /* previous value of PSW_UM */
+#define PSW_OUM 0x01000000 /* old value of PSW_UM */
+#define PSW_IE 0x00800000 /* interrupt enable bit in PSW */
+#define PSW_PIE 0x00400000 /* previous value of PSW_IE */
+#define PSW_OIE 0x00200000 /* old value of PSW_IE */
+#define PSW_PRIO_MASK 0x001F0000 /* bits to encode IRQ prio in PSW */
+
+
+Word cpuGetPC(void);
+void cpuSetPC(Word addr);
+
+Word cpuGetReg(int regnum);
+void cpuSetReg(int regnum, Word value);
+
+Word cpuGetPSW(void);
+void cpuSetPSW(Word value);
+
+Bool cpuTestBreak(void);
+Word cpuGetBreak(void);
+void cpuSetBreak(Word addr);
+void cpuResetBreak(void);
+
+char *exceptionToString(int exception);
+
+Bool cpuStep(void);
+Bool cpuRun(void);
+
+
+#endif /* _CPU_H_ */
Index: monitor/monitor/Makefile
===================================================================
--- monitor/monitor/Makefile (nonexistent)
+++ monitor/monitor/Makefile (revision 16)
@@ -0,0 +1,31 @@
+#
+# Makefile for ECO32 ROM monitor
+#
+
+BUILD = ../../build
+
+SRC = start.s main.c command.c instr.c asm.c disasm.c \
+ boot.c cpu.c mmu.c getline.c romlib.c \
+ keyboard.s ../kbdtbls/kbdtbls.s display.s \
+ serial.s sctio-ctl.s sctio-ser.s end.s
+
+.PHONY: all install clean
+
+all: monitor.bin monitor.exo
+
+install: monitor.bin monitor.exo
+ mkdir -p $(BUILD)/monitor
+ cp monitor.bin $(BUILD)/monitor
+ cp monitor.exo $(BUILD)/monitor
+
+monitor.exo: monitor.bin
+ $(BUILD)/bin/bin2exo 0 monitor.bin monitor.exo
+
+monitor.bin: $(SRC)
+ $(BUILD)/bin/lcc -A -Wo-rom -Wl-rd -Wl0xC03F0000 \
+ -Wl-m -Wlmonitor.map -o monitor.bin $(SRC)
+
+clean:
+ rm -f *~
+ rm -f monitor.map monitor.bin
+ rm -f monitor.exo
Index: monitor/monitor/common.h
===================================================================
--- monitor/monitor/common.h (nonexistent)
+++ monitor/monitor/common.h (revision 16)
@@ -0,0 +1,27 @@
+/*
+ * common.h -- common definitions
+ */
+
+
+#ifndef _COMMON_H_
+#define _COMMON_H_
+
+
+#define PAGE_SHIFT 12 /* log2 of page size */
+#define PAGE_SIZE (1 << PAGE_SHIFT) /* page size in bytes */
+#define OFFSET_MASK (PAGE_SIZE - 1) /* mask for offset in page */
+#define PAGE_MASK (~OFFSET_MASK) /* mask for page number */
+
+
+typedef enum { false, true } Bool; /* truth values */
+
+
+typedef unsigned int Word; /* 32 bit quantities */
+typedef unsigned short Half; /* 16 bit quantities */
+typedef unsigned char Byte; /* 8 bit quantities */
+
+
+#define NULL ((void *) 0)
+
+
+#endif /* _COMMON_H_ */
Index: monitor/Makefile
===================================================================
--- monitor/Makefile (nonexistent)
+++ monitor/Makefile (revision 16)
@@ -0,0 +1,25 @@
+#
+# Makefile for building the ECO32 ROM monitor
+#
+
+BUILD = ../build
+
+DIRS = kbdtbls monitor
+
+.PHONY: all install clean
+
+all:
+ for i in $(DIRS) ; do \
+ $(MAKE) -C $$i all ; \
+ done
+
+install:
+ for i in $(DIRS) ; do \
+ $(MAKE) -C $$i install ; \
+ done
+
+clean:
+ for i in $(DIRS) ; do \
+ $(MAKE) -C $$i clean ; \
+ done
+ rm -f *~
Index: Makefile
===================================================================
--- Makefile (revision 15)
+++ Makefile (revision 16)
@@ -4,7 +4,7 @@
VERSION = 0.22
-DIRS = doc binutils sim simtest fpga hwtests
+DIRS = doc binutils sim simtest fpga hwtests monitor
BUILD = `pwd`/build
.PHONY: all compiler builddir clean dist