sigh. i dont know

This commit is contained in:
Nero 2020-02-28 19:55:00 +00:00
parent f4f89e8e48
commit 30ae244ef1
9 changed files with 110 additions and 212 deletions

4
.gitignore vendored
View File

@ -1,2 +1,2 @@
*.COM
*.BIN
*.bin
scripts/

3
.gitmodules vendored
View File

@ -1,3 +0,0 @@
[submodule "8080"]
path = HOST/8080
url = https://github.com/superzazu/8080.git

@ -1 +0,0 @@
Subproject commit ec5d2bd99cbf9286224675e5e46849277479ef82

View File

@ -1,149 +0,0 @@
// This file uses the 8080 emulator to run the test suite (roms in cpu_tests
// directory). It uses a simple array as memory.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "8080/i8080.h"
// memory callbacks
#define MEMORY_SIZE 0x10000
static uint8_t* memory = NULL;
static bool test_finished = 0;
static uint8_t rb(void* userdata, const uint16_t addr) {
return memory[addr];
}
static void wb(void* userdata, const uint16_t addr, const uint8_t val) {
memory[addr] = val;
}
uint16_t dma_addr;
uint8_t cur_disk = 'Z'-'A';
char filename[16];
void filename_from_fcb(void* userdata, uint16_t addr) {
i8080* const c = (i8080*) userdata;
memset(&filename, 0, sizeof(filename));
char* ptr = filename;
while(rb(c, addr) != '.' && rb(c, addr) > ' ') {
*ptr++ = rb(c, addr++);
}
if (rb(c, addr) == '.') {
addr++;
while(rb(c, addr) > ' ') {
*ptr++ = rb(c, addr++);
}
}
}
void filename_to_fcb(void* userdata, uint16_t addr) {
}
static uint8_t port_in(void* userdata, uint8_t port) {
i8080* const c = (i8080*) userdata;
uint16_t de = (c->d << 8) | c->e;
switch(c->c) {
case 2:
printf("%c", c->e);
break;
case 9:
do {
printf("%c", rb(c, de++));
} while(rb(c, de) != '$');
break;
case 15:
filename_from_fcb(userdata, de);
printf("filename: %s\n", filename);
exit(1);
break;
case 25:
c->a = cur_disk;
break;
case 26:
dma_addr = (c->d << 8) | c->e;
break;
default:
i8080_debug_output(c);
fprintf(stderr, "fatal: unknown syscall C=%02Xh (%d)\n", c->c, c->c);
exit(255);
}
return c->a;
}
static int load_file(const char* filename, uint16_t addr) {
FILE* f = fopen(filename, "rb");
if (f == NULL) {
fprintf(stderr, "error: can't open file '%s'.\n", filename);
return 1;
}
// file size check:
fseek(f, 0, SEEK_END);
size_t file_size = ftell(f);
rewind(f);
if (file_size + addr >= MEMORY_SIZE) {
fprintf(stderr, "error: file %s can't fit in memory.\n", filename);
return 1;
}
// copying the bytes in memory:
size_t result = fread(&memory[addr], sizeof(uint8_t), file_size, f);
if (result != file_size) {
fprintf(stderr, "error: while reading file '%s'\n", filename);
return 1;
}
fclose(f);
return 0;
}
int main(int argc, char** argv) {
memory = malloc(MEMORY_SIZE);
if (memory == NULL) {
return 255;
}
argc--;
if (!argc) {
fprintf(stderr, "No filename given\n");
return 255;
}
argv++;
i8080 cpu;
i8080_init(&cpu);
cpu.userdata = &cpu;
cpu.read_byte = rb;
cpu.write_byte = wb;
cpu.port_in = port_in;
memset(memory, 0, MEMORY_SIZE);
if (load_file(argv[0], 0x100) != 0) {
return 255;
}
cpu.pc = 0x100;
// inject "hlt" at 0x0000
memory[0x0000] = 0x76;
// inject "in a,0" at 0x0005 (cpm syscall)
memory[0x0005] = 0xDB;
memory[0x0006] = 0x00;
memory[0x0007] = 0xC9;
while (!cpu.halted) {
// i8080_debug_output(&cpu);
i8080_step(&cpu);
}
free(memory);
return cpu.a;
}

View File

@ -1,17 +1,14 @@
DISTFILES = $(PROGRAMS)
.PHONY: default
.PHONY: default bootstrap clean qemu-rom qemu-floppy
cp437.bin: src/cp437.bmp scripts/bmp2font
scripts/bmp2font $< $@
default: fdimage.img
vga11.bin: src/vga11.asm cp437.bin
nasm -o $@ $<
MAC.COM:
wget -N http://www.cpm.z80.de/download/mac-b.zip
unzip mac-b.zip
CP437.BIN: CP437.BMP HOST/bmp2font
HOST/bmp2font $< $@
HOST/em8080: HOST/8080/i8080.o HOST/em8080.o
scripts/%: src/scripts/%.c
mkdir -p scripts
gcc -o $@ $<
clean:
rm -f *.COM *.BIN HOST/bmp2font HOST/em8080 HOST/*.o
rm -f *.bin scripts/*

View File

@ -1,45 +0,0 @@
## Components
The BIOS is in the uppermost 2K of the memory area - it provides basic character and disk I/O functions.
It it expected to stay static and not be unloaded by the user program.
The BIOS may hook into interrupts if necessary to provide its functionality.
Depending on your hardware, a different BIOS binary may be used.
The BDOS is in the 2K below the BIOS, it provides a filesystem driver to work atop of the BIOS.
It is agnostic to the underlaying hardware configuration, but different depending on the instruction set.
A user program might overwrite memory up to the end of the BDOS.
Upon program exit, the BIOS will reload the BDOS from disk.
## Memory Layout
On a 8080, there are no segments, the addresses are as displayed.
On on the 8086, a single segment with a value of 0x0100 is assumed.
This implies that the first 4k of memory are not used.
The BIOS and BDOS may be recompiled for starting at a lower address, in this case,
the minimum memory requirement may be less than 64k.
|Start |Size |Function|
|------|---------|--------|
|0xF800|2k |BIOS / hw drivers|
|0xF000|2k |BDOS|
|... |... |BDOS data area, disk deblocking buffers|
|SP |var |Stack, growing down|
|... |... |Free memory|
|... |var |Heap, growing up|
|0x0100|var |Transient Program Area|
|0x0080|128 bytes|Command line and disk buffer|
|0x006C|20 bytes |Pre-filled FCB 2|
|0x005C|16 bytes |Pre-filled FCB 1|
|0x0008|84 bytes |BIOS data area, specific to BIOS implementation|
|0x0005|3 bytes |Jump code for BDOS|
|0x0004|1 byte |default drive for BDOS|
|0x0003|1 byte |may be used as iobyte by BIOS|
|0x0000|3 bytes |Jump to BIOS warm boot entry point / program exit|
## Application program interface
It is using the `call 5` convention with CP/M compatible syscall numbers.
File I/O is done via FCB blocks.

View File

Before

Width:  |  Height:  |  Size: 2.1 KiB

After

Width:  |  Height:  |  Size: 2.1 KiB

99
src/vga11.asm Normal file
View File

@ -0,0 +1,99 @@
org 0x7C00
cols: equ 80
rows: equ 30
main:
mov ax, cs
mov ds, ax
mov es, ax
mov ss, ax
xor sp, sp
mov ah, 0x42
mov si, dap
int 0x13
mov ax, 0x0011
int 0x10
mov di, txtbuf
.loop:
call sync
xor ax, ax
int 0x16
stosb
jmp .loop
hlt:
hlt
jmp hlt
sync:
push ax
push si
push di
push es
mov si, txtbuf
mov ax, 0xA000
mov es, ax
mov di, 0
mov bx, font
mov cx, rows
.loop:
call charline
loop .loop
pop es
pop di
pop si
pop ax
ret
charline:
push bx
push cx
mov cx, 8
.loop:
call scanline
call scanline
inc bh
loop .loop
add si, cols
pop cx
pop bx
ret
scanline:
push si
push cx
mov cx, cols
.loop:
lodsb
mov bl, al
mov al, [bx]
stosb
loop .loop
pop cx
pop si
ret
dap:
db 0x10
db 1
dw 20
dw font, 0
dq 1
times (510 - ($-$$)) nop
dw 0xAA55
font:
incbin "cp437.bin"
txtbuf:
times (rows * cols) db 0
end: