-
Touched up bin2mif.py
05/27/2021 at 10:21 • 0 commentsI touched up the binary to MIF utility (bin2mif.py) to set the address to octal. That makes it easier to map to the PAL list file. The top of the MIF file now looks like:
-- File: sievePlusLoaders.mif -- Generated by bin2mif.py -- DEPTH = 4096; WIDTH = 12; ADDRESS_RADIX = OCTAL; DATA_RADIX = OCTAL; CONTENT BEGIN 0000: 0000 0000 0000 0000 0000 0000 0000 0000; 0010: 0000 0000 0000 0000 0000 0000 0000 0000; 0020: 0000 0000 0000 0000 0000 0000 0000 0000; 0030: 0000 0000 0000 0000 0000 0000 0000 0000; 0040: 0000 0000 0000 0000 0000 0000 0000 0000; 0050: 0000 0000 0000 0000 0000 0000 0000 0000; 0060: 0000 0000 0000 0000 0000 0000 0000 0000; 0070: 0000 0000 0000 0000 0000 0000 0000 0000; 0100: 0000 0000 0000 0000 0000 0000 0000 0000; 0110: 0000 0000 0000 0000 0000 0000 0000 0000; 0120: 0000 0000 0000 0000 0000 0000 0000 0000; 0130: 0000 0000 0000 0000 0000 0000 0000 0000; 0140: 0000 0000 0000 0000 0000 0000 0000 0000; 0150: 0000 0000 0000 0000 0000 0000 0000 0000; 0160: 0000 0000 0000 0000 0000 0000 0000 0000; 0170: 0000 0000 0000 0000 0000 0000 0000 0000; 0200: 7300 6046 7200 1377 3010 1376 3022 3410; 0210: 2022 5207 7305 3020 7200 1020 4775 1423; 0220: 0024 7440 5247 7200 1020 3021 7300 1021; 0230: 1020 7430 5247 3021 1021 4775 1024 7040;
This correlates to the lst file:
13 14 0010 *10 15 00010 0000 incval, 0 / For autoincrementing 16 0020 *20 / Our variables 17 00020 0000 checking, 0 18 00021 0000 multiple, 0 19 00022 0000 ii, 0 20 00023 0000 ptr, 0 / Calculated memory location and mask 21 00024 0000 memmask, 0 22 5000 *5000 23 05000 0000 sieve, 0 / Sieve is 512 words, so location 5000 to 5777 24 25 0200 *200 / start of program 26 00200 7300 main, CLA CLL 27 00201 6046 TLS / Reset the TTY 28 29 / Clear the array 30 00202 7200 CLA 31 00203 1377 TAD (sieve-1) / put address of array-1 in incval 32 00204 3010 DCA incval 33 00205 1376 TAD (-words) / Put -size of array in i 34 00206 3022 DCA ii 35 00207 3410 loop1, DCA I incval / Store 0 in successive locations 36 00210 2022 ISZ ii / until end of array 37 00211 5207 JMP loop1 38 39 / Do the marking 40 00212 7305 CLA CLL IAC RAL / 2 41 00213 3020 DCA checking / initialize checking variable 42 00214 7200 loop2, CLA 43 00215 1020 TAD checking / get checking variable 44 00216 4775@ JMS calcpm 45 00217 1423 TAD I ptr / get memory word 46 00220 0024 AND memmask / get the bit
Now I'm trying to get the bin loader working over the serial port. Not sure what the serial protocol is. Must 8 bits of data, though.
-
Demonstration Video
05/23/2021 at 15:37 • 0 commentsPut together a short highlights video.
-
Front Panel Operation
05/22/2021 at 12:58 • 0 commentsPCB arrived. Built it. Tested it. It took a lot of FPGA tweeks to get it working like I want.
Pushbuttons
- DISP - cycles between DISP LEDs [AC, MD, MADR, PC]
- STEP - single step the CPU
- LDPC - load the PC from the bottom slide switches
- DEP - store the value from the bottom slide switches to the memory at the current Program Counter
- LDA - load the Accumulator from the bottom slide switches
- RES - reset the CPU
- PB1 - spare
Slide Switches
- 0-11 value that is loaded by the pushbuttons. Also the address value in MD mode
- LNK - set the LINK bit when the accumulator is loaded (not yet implemented?)
- RUN/HALT - up = Run the CPU from the current PC, down = Halt the CPU
LEDs
- 0-11 - displays the value in the register/memory location selected by the DISP LEDs and selected by the DISP pushbutton
- PC - display the Program Counter value on 0-11 LEDs
- MADR - Not used
- MD - displays the data in memory at the current PC on 0-11 LEDs
- AC - displays the Accumulator value on 0-11 LEDs
- LINK - display the link bit (not yet implemented?)
- RUN - illuminated when the CPU is running, off when the CPU is halted
- PWR - power LED
Mounted above FPGA Card
-
Ported to EP2C5 (Multicomp) FPGA
05/17/2021 at 20:28 • 0 commentsPorted the design to the original Multicomp FPGA. Works great.
Webpage for FPGA adapter card.
Fills up the Internal SRAM resources. Room for more logic left over.
-
Interpreting DEC BIN Files
05/16/2021 at 11:27 • 1 commentData Section
Here's a look at the echo list file vs hex dump of the binary file for the data section.
The header is demarked as values of 0x80.
Addresses are marked as values of 0x40-0x4F. The data value follows. This is shown to be more complicated in the above example where the last item data is placed at 400 which is after the code. To fix this, bin2mif would need to keep track of this and do the writes.
The weird part is the address encoding. For the first locations, the address in the listing is in octal and the address in the hex window is in hex. That makes sense. However, for the final value the number is 400 in both windows - strange? Not really since the upper 2 bits of the second byte get discarded.
Code Section
Now, take a look at the code section. The mapping is the same here:
The first cut at the bin2mif program read in the binary data until it found the 4200 (oct) and snagged the following data. That worked fine for the contiguous section of code, but didn't work for section after the code which had to be manually copied in the In System Memory Editor:
It would be nice if the bin2mif utility could handle this. This transition is also marked in the same way:
Fixing bin2mif, then, involves detecting the same address bit and filling out the gap between the end of the previous data and the start of the next data section.
Another way would be to have a 4K Word array and fill it as data arrives. That's arguably the best way to handle this.
Re-Wrote bin2mif.py
Re-factored the bin2mif code to interpret the addresses. It worked with the echo code. Command line was:
python ..\bin2mif_2.py echo.bin > echo.mif
Tested with the sieve code and it worked:
Success!
-
Running echo.pal example
05/15/2021 at 18:07 • 0 commentsThe echo.pal example program reads characters from the serial port and echos them out as they are entered. When Enter is pressed, the entire line gets sent to the serial port.
In the previous log I created a utility bin2mif that does a simple translation of the DEC bin file into a memory initialization file. The program only copies code sections and doesn't deal with non-contiguous code sections. This limitation is fine for the data since it should all be set to zero anyway but it's a problem for the non-contiguous code sections in echo.pal.
Here's the echo.lst file:
1 / Serial port test (echo) 2 / http://homepage.divms.uiowa.edu/~jones/pdp8/man/tty.html 3 0010 *10 4 00010 0000 linep, 0 5 0020 *20 6 00020 0000 saved, 0 7 00021 0000 count, 0 8 0400 *400 / Line stored here 9 00400 0000 line, 0 10 0200 *200 11 00200 7200 CLA / Clear Accumulator 12 00201 6046 TLS / Teleprinter Load and start 13 00202 7200 newl, CLA / Clear Accumulator 14 00203 1377 TAD (line-1) 15 00204 3010 DCA linep 16 00205 6031 newc, KSF / Keyboard Skip if Flag (input data is ready) 17 00206 5205 JMP .-1 / 18 00207 6036 KRB / Keyboard Read and begin next read 19 00210 0376 AND (177) / Get rid of parity bit 20 00211 6041 TSF / Teleprinter Skip if Flag 21 00212 5211 JMP .-1 22 00213 6046 TLS / Teleprinter Load and start (Echo it) 23 00214 3020 DCA saved / save a copy 24 00215 1020 TAD saved 25 00216 3410 DCA I linep / store it away 26 00217 1020 TAD saved 27 00220 1375 TAD (-15) / CR character? 28 00221 7440 SZA / finished line if so - Skip next instruction if Zero Accumulator 29 00222 5205 JMP newc 30 00223 1374 TAD (12) / Echo line feed as well 31 00224 6041 TSF / Teleprinter Skip if Flag 32 00225 5224 JMP .-1 33 00226 6046 TLS / Teleprinter Load and start (Echo it) 34 / Now echo the line 35 00227 7200 CLA / Clear Accumulator 36 00230 1373 TAD (-line) 37 00231 1010 TAD linep / get number of characters 38 00232 7040 CMA / minus the number 39 00233 3021 DCA count 40 00234 1377 TAD (line-1) / reset starting address 41 00235 3010 DCA linep 42 00236 7200 echoc, CLA / Clear Accumulator 43 00237 1410 TAD I linep / get character 44 00240 6041 TSF / Teleprinter Skip if Flag 45 00241 5240 JMP .-1 46 00242 6046 TLS / Teleprinter Load and start 47 00243 2021 ISZ count / Increment and store 48 00244 5236 JMP echoc 49 00245 7200 CLA / Clear Accumulator 50 00246 1374 TAD (12) 51 00247 6041 TSF / Teleprinter Skip if Flag 52 00250 5247 JMP .-1 53 00251 6046 TLS / Teleprinter Load and start 54 00252 5202 JMP newl 00373 7400 00374 0012 00375 7763
The problem here is the values in locations 373-375 (oct). They get placed immediately after the code at 263-255, These can be manually inserted using the In System Memory editor.
The Quartus In System Memory Editor can be used to do an export of the data (first select all). Saved the code as echo_fixed.mif.
The result is that the echo code runs on the PDP-8 FPGA.
-
PDP-8 Software Toolchain
04/24/2021 at 20:24 • 0 commentsBuild PDP-8 Assembler Tool
- Assembler macro8x.c generates binary (DEC bin) files from PDP-8 Assembly Language files
- Notes from macro8x.c source code
This program has been built and successfully executed on: Linux (80486 CPU) using gcc RS/6000 (AIX 3.2.5) Borland C++ version 3.1 (large memory model) Borland C++ version 4.52 (large memory model) with no modifications to the source code. On UNIX type systems, store the the program as the pal command and on PC type systems, store it as pal.exe
- Command line to compile assembler (under Linux GCC):
gcc macro8x.c
- macro8x.c would not compile under VisualStudio
- macro8x.c source compiled without error under Linux Mint under VirtualBox
Simple Test Program
I wrote a very simple test program, easy.pal . The program continually increments a memory location, at 10 (oct).
- Compile easy.pal code using:
../macro8x -x easy.pal
List file is:
1 0010 *10 2 00010 0000 linep, 0 3 0200 *200 4 00200 2010 ISZ linep 5 00201 5200 JMP .-1 6 00202 5200 JMP .-2 7 No detected errors
The binary file from macro8x easy.bin as viewed in HxD (as 16-bit hex values) is:
Bin to MIF Utility
The output of the macro8x assembler is DEC bin loader format. The DEC bin format is described in DEC-OO- LBAA-D:
Wrote a utility, bin2mif.py to convert binary loader data to Altera Memory Initialization (MIF) files. The program:
- Ignores the (0x80) header values and ignores the data section (0x4008 0x0000 values)
- Looks for the code section (starting with 0x4200)
- Assumes code starts at 200 (oct). This could be pulled from the 0x4200 location,
- Pads the first 200 (oct) locations with 0000 (oct).
Here's the output:
-- Generated by bin2mif.py -- DEPTH = 131; WIDTH = 12; ADDRESS_RADIX = DECIMAL; DATA_RADIX = OCTAL; CONTENT BEGIN 0000: 0000 0000 0000 0000 0000 0000 0000 0000; 0008: 0000 0000 0000 0000 0000 0000 0000 0000; 0016: 0000 0000 0000 0000 0000 0000 0000 0000; 0024: 0000 0000 0000 0000 0000 0000 0000 0000; 0032: 0000 0000 0000 0000 0000 0000 0000 0000; 0040: 0000 0000 0000 0000 0000 0000 0000 0000; 0048: 0000 0000 0000 0000 0000 0000 0000 0000; 0056: 0000 0000 0000 0000 0000 0000 0000 0000; 0064: 0000 0000 0000 0000 0000 0000 0000 0000; 0072: 0000 0000 0000 0000 0000 0000 0000 0000; 0080: 0000 0000 0000 0000 0000 0000 0000 0000; 0088: 0000 0000 0000 0000 0000 0000 0000 0000; 0096: 0000 0000 0000 0000 0000 0000 0000 0000; 0104: 0000 0000 0000 0000 0000 0000 0000 0000; 0112: 0000 0000 0000 0000 0000 0000 0000 0000; 0120: 0000 0000 0000 0000 0000 0000 0000 0000; 0128: 2010 5200 5200; END;
Loaded the easy.mif file. Got the expected warning loading it into Quartus (it's OK).
Critical Warning (127005): Memory depth (4096) in the design file differs from memory depth (131) in the Memory Initialization File "C:/Users/HPz420/Documents/GitHub/Doug Gilliland/Linux-68k/pdp8/ PDP8_Programs/easy.mif" -- setting initial value for remaining addresses to 0.
Ran. It worked great. The code is at the correct place and increments the location 10 (oct).
Code loaded at 200 (oct) which is 0x80 (hex), Verified data changes with In System Memory Content Editor.
And again:
Success!