mirror of
https://github.com/romychs/Ocean-240.2-Emulator.git
synced 2026-04-21 11:03:21 +03:00
256b disk sec
This commit is contained in:
parent
b133807f05
commit
50f4e2521f
24
main.go
24
main.go
@ -23,7 +23,7 @@ var BuildTime = "2026-03-01"
|
||||
//go:embed hex/format.hex
|
||||
var serialBytes []byte
|
||||
|
||||
//go:embed bin/TYPE.COM
|
||||
//go:embed bin/MB.COM
|
||||
var ramBytes []byte
|
||||
|
||||
var needReset = false
|
||||
@ -72,7 +72,13 @@ func mainWindow(computer *okean240.ComputerType, emuConfig *config.OkEmuConfig)
|
||||
|
||||
raster := canvas.NewRasterWithPixels(
|
||||
func(x, y, w, h int) color.Color {
|
||||
return computer.GetPixel(uint16(x/2), uint16(y/2))
|
||||
var xx uint16
|
||||
if computer.ScreenWidth() == 512 {
|
||||
xx = uint16(x)
|
||||
} else {
|
||||
xx = uint16(x) / 2
|
||||
}
|
||||
return computer.GetPixel(xx, uint16(y/2))
|
||||
})
|
||||
raster.Resize(fyne.NewSize(512, 512))
|
||||
raster.SetMinSize(fyne.NewSize(512, 512))
|
||||
@ -130,7 +136,7 @@ func emulator(computer *okean240.ComputerType, raster *canvas.Raster, label *wid
|
||||
var freq uint64 = 0
|
||||
|
||||
nextSecond := time.Now().Add(time.Second).UnixMicro()
|
||||
curScrWidth := 256
|
||||
//curScrWidth := 256
|
||||
for range ticker.C {
|
||||
if needReset {
|
||||
computer.Reset(emuConfig)
|
||||
@ -159,12 +165,12 @@ func emulator(computer *okean240.ComputerType, raster *canvas.Raster, label *wid
|
||||
// redraw screen here
|
||||
fyne.Do(func() {
|
||||
// check for screen mode changed
|
||||
if computer.ScreenWidth() != curScrWidth {
|
||||
curScrWidth = computer.ScreenWidth()
|
||||
newSize := fyne.NewSize(float32(curScrWidth*2), float32(computer.ScreenHeight()*2))
|
||||
raster.SetMinSize(newSize)
|
||||
raster.Resize(newSize)
|
||||
}
|
||||
//if computer.ScreenWidth() != curScrWidth {
|
||||
// curScrWidth = computer.ScreenWidth()
|
||||
// newSize := fyne.NewSize(float32(curScrWidth*2), float32(computer.ScreenHeight()*2))
|
||||
// raster.SetMinSize(newSize)
|
||||
// raster.Resize(newSize)
|
||||
//}
|
||||
// status for every 25 frames
|
||||
if frame%50 == 0 {
|
||||
label.SetText(fmt.Sprintf("Screen size: %dx%d F: %d", computer.ScreenWidth(), computer.ScreenHeight(), freq))
|
||||
|
||||
@ -5,7 +5,7 @@ import (
|
||||
"encoding/binary"
|
||||
"image/color"
|
||||
"okemu/config"
|
||||
fdc2 "okemu/okean240/fdc"
|
||||
"okemu/okean240/fdc"
|
||||
"okemu/okean240/pic"
|
||||
"okemu/okean240/pit"
|
||||
"okemu/okean240/usart"
|
||||
@ -17,7 +17,7 @@ import (
|
||||
)
|
||||
|
||||
type ComputerType struct {
|
||||
cpu z80em.Z80Type
|
||||
cpu *z80em.Z80Type
|
||||
memory Memory
|
||||
ioPorts [256]byte
|
||||
cycles uint64
|
||||
@ -28,10 +28,10 @@ type ComputerType struct {
|
||||
vRAM *RamBlock
|
||||
palette byte
|
||||
bgColor byte
|
||||
dd70 *pit.I8253
|
||||
dd72 *usart.I8251
|
||||
dd75 *pic.I8259
|
||||
fdc *fdc2.FloppyDriveController
|
||||
pit *pit.I8253
|
||||
usart *usart.I8251
|
||||
pic *pic.I8259
|
||||
fdc *fdc.FloppyDriveController
|
||||
kbdBuffer []byte
|
||||
vShift byte
|
||||
hShift byte
|
||||
@ -41,7 +41,6 @@ const VRAMBlock0 = 3
|
||||
const VRAMBlock1 = 7
|
||||
const VidVsuBit = 0x80
|
||||
const VidColorBit = 0x40
|
||||
const KbdBufferSize = 3
|
||||
|
||||
type ComputerInterface interface {
|
||||
Run()
|
||||
@ -75,7 +74,7 @@ func New(cfg *config.OkEmuConfig) *ComputerType {
|
||||
c.memory = Memory{}
|
||||
c.memory.Init(cfg.MonitorFile, cfg.CPMFile)
|
||||
|
||||
c.cpu = *z80em.New(&c)
|
||||
c.cpu = z80em.New(&c)
|
||||
|
||||
c.cycles = 0
|
||||
c.dd17EnableOut = false
|
||||
@ -88,10 +87,10 @@ func New(cfg *config.OkEmuConfig) *ComputerType {
|
||||
c.vShift = 0
|
||||
c.hShift = 0
|
||||
|
||||
c.dd70 = pit.NewI8253()
|
||||
c.dd72 = usart.NewI8251()
|
||||
c.dd75 = pic.NewI8259()
|
||||
c.fdc = fdc2.NewFDCType()
|
||||
c.pit = pit.New()
|
||||
c.usart = usart.New()
|
||||
c.pic = pic.New()
|
||||
c.fdc = fdc.New()
|
||||
|
||||
return &c
|
||||
}
|
||||
@ -120,9 +119,9 @@ func (c *ComputerType) Do() int {
|
||||
//}
|
||||
ticks := uint64(c.cpu.RunInstruction())
|
||||
c.cycles += ticks
|
||||
//if c.cpu.PC == 0x2C2 {
|
||||
// log.Debugf("%4X: H:%X L:%X", c.cpu.PC, c.cpu.H, c.cpu.L)
|
||||
//}
|
||||
if c.cpu.PC == 0xFF26 {
|
||||
log.Debugf("%4X: H:%X L:%X A:%X B: %X C: %X D: %X E: %X", c.cpu.PC, c.cpu.H, c.cpu.L, c.cpu.A, c.cpu.B, c.cpu.C, c.cpu.D, c.cpu.E)
|
||||
}
|
||||
return int(ticks)
|
||||
}
|
||||
|
||||
@ -140,16 +139,16 @@ func (c *ComputerType) GetPixel(x uint16, y uint16) color.RGBA {
|
||||
}
|
||||
|
||||
y += uint16(c.vShift) & 0x00ff
|
||||
x += uint16(c.hShift) & 0x00ff
|
||||
x += uint16(c.hShift-7) & 0x00ff
|
||||
|
||||
// Color 256x256 mode
|
||||
addr = ((x & 0xf8) << 6) | (y & 0xff)
|
||||
if c.vShift != 0 {
|
||||
addr -= 8
|
||||
}
|
||||
addr = ((x & 0xf8) << 6) | y
|
||||
//if c.vShift != 0 {
|
||||
// addr -= 8
|
||||
//}
|
||||
|
||||
cl := (c.vRAM.memory[addr&0x3fff] >> (x & 0x07)) & 1
|
||||
cl |= (c.vRAM.memory[(addr+0x100)&0x3fff] >> (x & 0x07)) & 1 << 1
|
||||
cl |= ((c.vRAM.memory[(addr+0x100)&0x3fff] >> (x & 0x07)) & 1) << 1
|
||||
if cl == 0 {
|
||||
resColor = BgColorPalette[c.bgColor]
|
||||
} else {
|
||||
@ -159,18 +158,22 @@ func (c *ComputerType) GetPixel(x uint16, y uint16) color.RGBA {
|
||||
if x > 511 {
|
||||
return CWhite
|
||||
}
|
||||
|
||||
// Shifts
|
||||
y += uint16(c.vShift) & 0x00ff
|
||||
x += uint16(c.hShift-7) & 0x001ff
|
||||
|
||||
// Mono 512x256 mode
|
||||
y += uint16(c.vShift)
|
||||
addr = ((x & 0xf8) << 5) | (y & 0xff)
|
||||
pix := c.vRAM.memory[addr]&(1<<x) != 0
|
||||
addr = ((x & 0x1f8) << 5) | y
|
||||
pix := c.vRAM.memory[addr] >> (x & 0x07) & 1
|
||||
if c.palette == 6 {
|
||||
if !pix {
|
||||
if pix == 0 {
|
||||
resColor = CBlack
|
||||
} else {
|
||||
resColor = CLGreen
|
||||
}
|
||||
} else {
|
||||
if !pix {
|
||||
if pix == 0 {
|
||||
resColor = BgColorPalette[c.bgColor]
|
||||
} else {
|
||||
resColor = MonoPalette[c.bgColor]
|
||||
@ -194,17 +197,17 @@ func (c *ComputerType) Cycles() uint64 {
|
||||
|
||||
func (c *ComputerType) TimerClk() {
|
||||
// DD70 KR580VI53 CLK0, CKL1 @ 1.5MHz
|
||||
c.dd70.Tick(0)
|
||||
c.dd70.Tick(1)
|
||||
c.pit.Tick(0)
|
||||
c.pit.Tick(1)
|
||||
|
||||
// IRQ from timer
|
||||
if c.dd70.Fired(0) {
|
||||
c.dd75.SetIRQ(RstTimerNo)
|
||||
if c.pit.Fired(0) {
|
||||
c.pic.SetIRQ(RstTimerNo)
|
||||
//c.ioPorts[PIC_DD75RS] |= Rst4Mask
|
||||
}
|
||||
// clock for SIO KR580VV51
|
||||
if c.dd70.Fired(1) {
|
||||
c.dd72.Tick()
|
||||
if c.pit.Fired(1) {
|
||||
c.usart.Tick()
|
||||
}
|
||||
}
|
||||
|
||||
@ -217,7 +220,7 @@ func (c *ComputerType) SaveFloppy() {
|
||||
}
|
||||
|
||||
func (c *ComputerType) SetSerialBytes(bytes []byte) {
|
||||
c.dd72.SetRxBytes(bytes)
|
||||
c.usart.SetRxBytes(bytes)
|
||||
}
|
||||
|
||||
func (c *ComputerType) SetRamBytes(bytes []byte) {
|
||||
|
||||
@ -321,7 +321,7 @@ func (f *FloppyDriveController) SaveFloppy() {
|
||||
|
||||
}
|
||||
|
||||
func NewFDCType() *FloppyDriveController {
|
||||
func New() *FloppyDriveController {
|
||||
sec := [SizeInSectors]SectorType{}
|
||||
for i := 0; i < SizeInSectors; i++ {
|
||||
sec[i] = make([]byte, SectorSize)
|
||||
|
||||
@ -14,13 +14,13 @@ func (c *ComputerType) IORead(port uint16) byte {
|
||||
switch port & 0x00ff {
|
||||
case PIC_DD75A:
|
||||
// PIO xx59, get IRR register
|
||||
return c.dd75.IRR()
|
||||
return c.pic.IRR()
|
||||
case UART_DD72RR:
|
||||
// USART VV51 CMD
|
||||
return c.dd72.Status()
|
||||
return c.usart.Status()
|
||||
case UART_DD72RD:
|
||||
// USART VV51 Data
|
||||
return c.dd72.Receive()
|
||||
return c.usart.Receive()
|
||||
case KBD_DD78PA:
|
||||
// Keyboard data
|
||||
return c.ioPorts[KBD_DD78PA]
|
||||
@ -79,23 +79,23 @@ func (c *ComputerType) IOWrite(port uint16, val byte) {
|
||||
c.hShift = val
|
||||
case TMR_DD70CTR:
|
||||
// Timer VI63 config register
|
||||
c.dd70.Configure(val)
|
||||
c.pit.Configure(val)
|
||||
case TMR_DD70C1:
|
||||
// Timer VI63 counter0 register
|
||||
c.dd70.Load(0, val)
|
||||
c.pit.Load(0, val)
|
||||
case TMR_DD70C2:
|
||||
// Timer VI63 counter1 register
|
||||
c.dd70.Load(1, val)
|
||||
c.pit.Load(1, val)
|
||||
case TMR_DD70C3:
|
||||
// Timer VI63 counter2 register
|
||||
c.dd70.Load(2, val)
|
||||
c.pit.Load(2, val)
|
||||
|
||||
case UART_DD72RR:
|
||||
// USART VV51 CMD
|
||||
c.dd72.Command(val)
|
||||
c.usart.Command(val)
|
||||
case UART_DD72RD:
|
||||
// USART VV51 Data
|
||||
c.dd72.Send(val)
|
||||
c.usart.Send(val)
|
||||
case FDC_CMD:
|
||||
c.fdc.SetCmd(val)
|
||||
case FDC_DATA:
|
||||
|
||||
@ -10,7 +10,7 @@ func (c *ComputerType) PutKey(key *fyne.KeyEvent) {
|
||||
if code > 0 {
|
||||
//log.Debugf("PutKey keyName: %s", key.Name)
|
||||
c.ioPorts[KBD_DD78PA] = code
|
||||
c.dd75.SetIRQ(RstKbdNo)
|
||||
c.pic.SetIRQ(RstKbdNo)
|
||||
}
|
||||
|
||||
}
|
||||
@ -20,7 +20,7 @@ func (c *ComputerType) PutRune(key rune) {
|
||||
//log.Debugf("Put Rune: %c Lo: %x, Hi: %x", key, key&0xff, key>>8)
|
||||
|
||||
c.ioPorts[KBD_DD78PA] = byte(key & 0xff)
|
||||
c.dd75.SetIRQ(RstKbdNo)
|
||||
c.pic.SetIRQ(RstKbdNo)
|
||||
}
|
||||
|
||||
/*
|
||||
@ -38,7 +38,7 @@ func (c *ComputerType) PutRune(key rune) {
|
||||
|
||||
func (c *ComputerType) PutCtrlKey(key byte) {
|
||||
c.ioPorts[KBD_DD78PA] = key
|
||||
c.dd75.SetIRQ(RstKbdNo)
|
||||
c.pic.SetIRQ(RstKbdNo)
|
||||
//c.ioPorts[PIC_DD75RS] |= Rst1Mask
|
||||
c.ioPorts[KBD_DD78PB] &= 0x1f | 0x20
|
||||
}
|
||||
|
||||
@ -47,7 +47,7 @@ func (c *I8259) SetIRQ(irq byte) {
|
||||
}
|
||||
}
|
||||
|
||||
func NewI8259() *I8259 {
|
||||
func New() *I8259 {
|
||||
return &I8259{
|
||||
irr: 0,
|
||||
}
|
||||
|
||||
@ -47,7 +47,7 @@ type I8253Interface interface {
|
||||
Start(chNo int) bool
|
||||
}
|
||||
|
||||
func NewI8253() *I8253 {
|
||||
func New() *I8253 {
|
||||
return &I8253{
|
||||
//chNo: 0,
|
||||
channel: [3]Timer8253Ch{
|
||||
|
||||
@ -4,7 +4,7 @@ import "fyne.io/fyne/v2"
|
||||
|
||||
var RemapCmdKey = map[fyne.KeyName]byte{
|
||||
fyne.KeyEscape: 0x1B,
|
||||
fyne.KeyReturn: 0x0A,
|
||||
fyne.KeyReturn: 0x0D,
|
||||
fyne.KeyTab: 0x09,
|
||||
fyne.KeyBackspace: 0x08,
|
||||
fyne.KeyInsert: 0x00,
|
||||
@ -29,7 +29,7 @@ var RemapCmdKey = map[fyne.KeyName]byte{
|
||||
fyne.KeyF10: 0x00,
|
||||
fyne.KeyF11: 0x00,
|
||||
fyne.KeyF12: 0x00,
|
||||
fyne.KeyEnter: 0x0D,
|
||||
fyne.KeyEnter: 0x0A,
|
||||
fyne.KeyUnknown: 0x00,
|
||||
}
|
||||
|
||||
|
||||
@ -47,7 +47,7 @@ type I8251Interface interface {
|
||||
Receive() byte
|
||||
}
|
||||
|
||||
func NewI8251() *I8251 {
|
||||
func New() *I8251 {
|
||||
return &I8251{
|
||||
counter: 0,
|
||||
mode: 0,
|
||||
|
||||
Loading…
Reference in New Issue
Block a user