From 702559e907a6975095a635df5efff8ca373b2f91 Mon Sep 17 00:00:00 2001 From: OmniaX-Dev Date: Thu, 7 Nov 2024 12:36:04 +0100 Subject: [PATCH] Sync push --- extra/config/testMachine.dvm | 2 +- extra/dragon/cmos.dr | Bin 128 -> 128 bytes extra/dragon/disk1.dr | Bin 4194304 -> 4194304 bytes extra/dss/bios/data.dss | 5 +++ extra/dss/bios_api.dss | 6 +++- extra/dss/drake/bootsector.dss | 50 +++++++++++++++++++++------ extra/info/info | 4 +++ extra/info/todo.txt | 4 +++ src/hardware/VirtualDisplay.cpp | 22 ++++++++++-- src/hardware/VirtualDisplay.hpp | 6 ++++ src/hardware/VirtualIODevices.cpp | 55 +++++++++++++++++++++++++++--- src/hardware/VirtualIODevices.hpp | 15 ++++++++ 12 files changed, 149 insertions(+), 20 deletions(-) diff --git a/extra/config/testMachine.dvm b/extra/config/testMachine.dvm index 1c6dff5..ecf8ba2 100644 --- a/extra/config/testMachine.dvm +++ b/extra/config/testMachine.dvm @@ -7,7 +7,7 @@ fixed_clock = false clock_rate_sec = 5000 memory_extension_pages = 16 -screen_redraw_rate_per_second = 20 +screen_redraw_rate_per_second = 10 SingleColor_foreground = #009900FF SingleColor_background = #111111FF diff --git a/extra/dragon/cmos.dr b/extra/dragon/cmos.dr index f12d726fe6b7993e67646a00c643d772f3f748da..83fed246f22509159f6a23ea55a199e81ff4be6c 100644 GIT binary patch literal 128 WcmWf4`2SzHgNq@GL6l(t03!gY0|RRS literal 128 WcmWf4`2SzHLxdrUL6l(t03!gc#{+c$ diff --git a/extra/dragon/disk1.dr b/extra/dragon/disk1.dr index bf22e3c2eb89f166e56b839380a2c575b93a32f8..5432417d985a6d008c7550c9413c5ff5beae557e 100644 GIT binary patch delta 367 zcmW-ZyH3Jj0EOEEElL#%SWf>c77zgiui*W%IZ5&pqL1Jz?hFkvCvooX;NWcHJDBKO z;N;3e989!zI4587ogClyH9ySDqkh@)Y(>rKh3>%lo_t7Ak&4=P-i9JBo!f}ri=ik> z#f(_oNJZ(p|1BOO7Wd)uH>YPu1JMk|`gPKdeO`HXEE9B$dVcCTGT}KrQ##$AB^9kN zroo+25XEuHQW6bETA|fKE0t8F-D2=$R5jNO-i?~tew`RU=@AH((1;ijClZ8C7(|ko zA!dmbVG?u1Jdq|cghgbD9FZp$2%9Jn;g3TI!X*}oC89_y6CP0_%0z`&A*#eGQ6uU^ tgIFWhi6+q^Hi%7Pi`XW1h+U#hbcj7-pEw{6i6i2eI3Z4nvuB)t{Q|J0L1a#HQ9|O9&y$D_lw7B67T!IE$oEACjmR3!Bkcj!D3!uTM;X3L3{-Z zpTW*X>?{RAcZ-4HH!z(}$Lpkdy7y1(@rdJEr(_+sWiCU%(rlaH`^`E|tJ<>0WFEcV zm;oDIWxcwQP3Ah4ztA7NZJS#1=L*05$wMK$MYzHfT_Pv)!WV%kh;Gp%ilQWXMW5&w z1EMSjMJR^Euow{)k^V%&h^iPBV`5xPh*(UDDNz%3(Gb&OM$C#iF)tRxqF55kVnwWq eHL)%>#HQF1+hRxTiaoI}4#c5263366eEtIin^)EV diff --git a/extra/dss/bios/data.dss b/extra/dss/bios/data.dss index 983b4ac..f59753d 100644 --- a/extra/dss/bios/data.dss +++ b/extra/dss/bios/data.dss @@ -66,6 +66,8 @@ TEXT_SIGNLE_INVERT { MemoryAddresses.VGA + 0x0005 } TEXT_SIGNLE_STR { MemoryAddresses.VGA + 0x0006 } + FLAGS { MemoryAddresses.VGA + 0x007E } + MEMORY_CONTROLLER_X { MemoryAddresses.VGA + 0x0080 } MEMORY_CONTROLLER_X_BYTE { MemoryAddresses.VGA + 0x0080 + 1 } MEMORY_CONTROLLER_Y { MemoryAddresses.VGA + 0x0082 } @@ -116,6 +118,7 @@ REFRESH_SCREEN 0xE0 CLEAR_SCREEN 0xE1 + REDRAW_SCREEN 0xE2 @end @raw_export_end @export_comment BIOS_API " --\n" @@ -127,10 +130,12 @@ @group Sig_VGA_Text_16_Color CONTINUE 0x00 + SWAP_BUFFERS 0x10 WRITE_VRAM 0x11 FORCE_REFRESH_SCREEN 0xE0 FORCE_CLEAR_SCREEN 0xE1 + FORCE_REDRAW_SCREEN 0xE2 @end @raw_export_end @export_comment BIOS_API " --\n" diff --git a/extra/dss/bios_api.dss b/extra/dss/bios_api.dss index 9ca0c90..272eaeb 100644 --- a/extra/dss/bios_api.dss +++ b/extra/dss/bios_api.dss @@ -1,5 +1,5 @@ ## -- -## -- This file is automatically generated by the DragonAssembler (version 0.4.1618) +## -- This file is automatically generated by the DragonAssembler (version 0.4.1617) ## -- Please do not modify this file in any way. ## -- @@ -47,6 +47,7 @@ TEXT_SINGLE_CHAR { MemoryAddresses.VGA + 0x0004 } TEXT_SIGNLE_INVERT { MemoryAddresses.VGA + 0x0005 } TEXT_SIGNLE_STR { MemoryAddresses.VGA + 0x0006 } + FLAGS { MemoryAddresses.VGA + 0x007E } MEMORY_CONTROLLER_X { MemoryAddresses.VGA + 0x0080 } MEMORY_CONTROLLER_X_BYTE { MemoryAddresses.VGA + 0x0080 + 1 } MEMORY_CONTROLLER_Y { MemoryAddresses.VGA + 0x0082 } @@ -83,15 +84,18 @@ PRINT_STRING 0x07 REFRESH_SCREEN 0xE0 CLEAR_SCREEN 0xE1 + REDRAW_SCREEN 0xE2 @end ## -- ## These are signals used to comunicate with the video card's interface, when in TEXT16_COLOR mode. @group Sig_VGA_Text_16_Color CONTINUE 0x00 + SWAP_BUFFERS 0x10 WRITE_VRAM 0x11 FORCE_REFRESH_SCREEN 0xE0 FORCE_CLEAR_SCREEN 0xE1 + FORCE_REDRAW_SCREEN 0xE2 @end ## -- diff --git a/extra/dss/drake/bootsector.dss b/extra/dss/drake/bootsector.dss index 441fb3b..cee54a0 100644 --- a/extra/dss/drake/bootsector.dss +++ b/extra/dss/drake/bootsector.dss @@ -39,45 +39,55 @@ _drake_bootsector_entry_point: ## Enable Text16 Video Mode movb [VGA_Registers.VIDEO_MODE], VGA_VideoModes.TEXT_16_COLORS - ## Clear screen - push DefaultPalette.DarkBlue - push 1 - call $_clear_screen - ## Validate DPT Block mov ACC, [$dpt_block] jne $_invalid_dpt_block, 0xF1CA - ## Print system info - push 0 - call $_print_system_info - ## Init Keyboard driver push $_key_pressed ## KeyPressed handler address passed to the _init_keyboard subroutine push 1 call $_init_keyboard + ## Enable Double buffering + ## mov R2, [VGA_Registers.FLAGS] + ## or R2, 0b0000000000000001 + ## mov [VGA_Registers.FLAGS], ACC + ## @call(_clear_screen, DefaultPalette.DarkBlue) ## @_clear_screen(DefaultPalette.DarkBlue) - ## mov R10, 0x22 ## mov R8, { $dpt_block + DPTStructure.ENTRIES_START + (2 * DPTStructure.ENTRY_SIZE_B) + DPTStructure.ENTRY_PART_LBL } ## mov R9, $textCell ## int 0x30 jmp $_endless_loop -_invalid_dpt_block: +_invalid_dpt_block: ## TODO: Fix screen drawing on error push $invalid_dpt_block_str push 1 call $_print_error_msg + jmp $_main_end _endless_loop: + ## Clear screen + push DefaultPalette.DarkBlue + push 1 + call $_clear_screen + + ## Print system info + push 0 + call $_print_system_info + ## Draw main box push 0 call $_print_main_box + ## Swap the buffers + push 0 + call $_swap_buffers + jmp $_endless_loop +_main_end: hlt ## ========================================================================================================================= @@ -134,6 +144,24 @@ _clear_screen: ## _clear_screen(int8_t color) +## ========================================================================================================================= +_redraw_screen: + movb [VGA_Registers.SIGNAL], Sig_VGA_Text_16_Color.FORCE_REDRAW_SCREEN + ret +## ========================================================================================================================= + + + + +## ========================================================================================================================= +_swap_buffers: + movb [VGA_Registers.SIGNAL], Sig_VGA_Text_16_Color.SWAP_BUFFERS + ret +## ========================================================================================================================= + + + + ## ========================================================================================================================= _print_main_box: movb [$textCell.CoordX], 5 diff --git a/extra/info/info b/extra/info/info index 6a33bec..9451bfa 100644 --- a/extra/info/info +++ b/extra/info/info @@ -99,10 +99,14 @@ 0xE0: Refresh Screen 0xE1: Clear Screen + 0xE2: Redraw Screen 0x04: Text Single Color Character (1 Byte) 0x05: Text Single Color Inverted colors (1 Byte) 0x06: (2 bytes) Text Single Color Buffered String Address + 0x7E: Flags (2 Bytes) + 0b00000000.00000001: Double Buffering Enabled + 0b00000000.00000010: Disable Screen Redraw 0x80: Memory Controller 0x80: XCoordinate (2 Bytes) 0x84: YCoordinate (2 Bytes) diff --git a/extra/info/todo.txt b/extra/info/todo.txt index 587e598..550f816 100644 --- a/extra/info/todo.txt +++ b/extra/info/todo.txt @@ -1,3 +1,7 @@ +Runtime: + Add in place logic operators (and, or...) to ExtAlu CPU Extension + Implement native flags operators (set, zero, toggle) + Assembler: Add subroutine address export functionality diff --git a/src/hardware/VirtualDisplay.cpp b/src/hardware/VirtualDisplay.cpp index 975aed8..23974f3 100644 --- a/src/hardware/VirtualDisplay.cpp +++ b/src/hardware/VirtualDisplay.cpp @@ -70,11 +70,10 @@ namespace dragon } } + m_redrawScreen = m_redrawScreen && !DragonRuntime::vGraphicsInterface.readFlag(hw::interface::Graphics::tFlags::ScreenRedrawDisabled); if (m_redrawScreen) { - m_renderer.updateBuffer(); - DragonRuntime::cpu.handleInterrupt(data::InterruptCodes::Text16ModeScreenRefreshed, true); - m_redrawScreen = false; + __redraw_screen(); } m_renderer.displayBuffer(); } @@ -170,6 +169,15 @@ namespace dragon m_redrawScreen = true; m_refreshScreen = true; } + else if (signal == tSignalValues::RedrawScreen) + { + __redraw_screen(); + } + else if (signal == tSignalValues::Text16Color_SwapBuffers) + { + DragonRuntime::vGraphicsInterface.swapBuffers_16Colors(); + __redraw_screen(); + } } else return; mem.write8(vga_addr + tRegisters::Signal, tSignalValues::Continue); @@ -197,6 +205,14 @@ namespace dragon void VirtualDisplay::onSlowUpdate(void) { } + void VirtualDisplay::__redraw_screen(void) + { + m_renderer.updateBuffer(); + DragonRuntime::cpu.handleInterrupt(data::InterruptCodes::Text16ModeScreenRefreshed, true); + m_redrawScreen = false; + m_refreshScreen = true; + } + void VirtualDisplay::single_text_add_char_to_line(char c) { auto& config = DragonRuntime::machine_config; diff --git a/src/hardware/VirtualDisplay.hpp b/src/hardware/VirtualDisplay.hpp index c7109c8..0545ce5 100644 --- a/src/hardware/VirtualDisplay.hpp +++ b/src/hardware/VirtualDisplay.hpp @@ -21,6 +21,8 @@ namespace dragon inline static constexpr uint8_t TextSingleInvertColors = 0x05; inline static constexpr uint8_t TextSingleString = 0x06; + inline static constexpr uint8_t Flags = 0x7E; + inline static constexpr uint8_t MemControllerX = 0x80; inline static constexpr uint8_t MemControllerY = 0x82; inline static constexpr uint8_t MemControllerChar = 0x84; @@ -43,10 +45,12 @@ namespace dragon inline static constexpr uint8_t TextSingleColor_DirectPrintBuffNoFlush = 0x06; inline static constexpr uint8_t TextSingleColor_DirectPrintString = 0x07; + inline static constexpr uint8_t Text16Color_SwapBuffers = 0x10; inline static constexpr uint8_t Text16Color_WriteMemory = 0x11; inline static constexpr uint8_t RefreshScreen = 0xE0; inline static constexpr uint8_t ClearSCreen = 0xE1; + inline static constexpr uint8_t RedrawScreen = 0xE2; }; public: void onInitialize(void) override; @@ -59,6 +63,8 @@ namespace dragon inline void redrawScreen(void) { m_redrawScreen = true; } private: + void __redraw_screen(void); + void single_text_add_char_to_line(char c); void single_text_add_char_to_buffer(char c); void single_text_flush_buffer(void); diff --git a/src/hardware/VirtualIODevices.cpp b/src/hardware/VirtualIODevices.cpp index be41ba4..1b7d03c 100644 --- a/src/hardware/VirtualIODevices.cpp +++ b/src/hardware/VirtualIODevices.cpp @@ -662,6 +662,9 @@ namespace dragon { m_videoMemory.init(0xFFFF); m_vramStart = data::MemoryMapAddresses::VideoCardInterface_End - data::MemoryMapAddresses::VideoCardInterface_Start; + m_16Color_frameSize = RawTextRenderer::CONSOLE_CHARS_H * RawTextRenderer::CONSOLE_CHARS_V * m_16Color_cellSize; + m_16Color_currentFrameAddr = m_vramStart; + m_16Color_secondFrameAddr = m_vramStart + m_16Color_frameSize; } int8_t Graphics::read8(uint16_t addr) @@ -706,6 +709,28 @@ namespace dragon return value; } + bool Graphics::readFlag(uint8_t flg) + { + if (flg >= 16) return false; + int16_t outValue = 0; + if (!m_videoMemory.r_Word(VirtualDisplay::tRegisters::Flags, outValue)) + return false; //TODO: Error + m_tempFlags.value = outValue; + return ostd::Bits::get(m_tempFlags, flg); + } + + void Graphics::setFlag(uint8_t flg, bool val) + { + if (flg >= 16) return; + int16_t outValue = 0; + if (!m_videoMemory.r_Word(VirtualDisplay::tRegisters::Flags, outValue)) + return; //TODO: Error + m_tempFlags.value = outValue; + ostd::Bits::val(m_tempFlags, flg, val); + if (!m_videoMemory.w_Word(VirtualDisplay::tRegisters::Flags, m_tempFlags.value)) + return; //TODO: Error + } + ostd::ByteStream* Graphics::getByteStream(void) { return &m_videoMemory.getData(); @@ -714,7 +739,7 @@ namespace dragon bool Graphics::readVRAM_16Colors(uint8_t x, uint8_t y, Graphics::tText16_Cell& outTextCell) { uint16_t cellOffset = static_cast(CONVERT_2D_1D(x, y, RawTextRenderer::CONSOLE_CHARS_H)) * 4; - cellOffset += m_vramStart; + cellOffset += m_16Color_currentFrameAddr; int8_t outVal = 0; if (!m_videoMemory.r_Byte(cellOffset + tText16_CellStructure::character, outVal)) return false; //TODO: Error @@ -726,12 +751,15 @@ namespace dragon return false; //TODO: Error outTextCell.foregroundColor = outVal; return true; - } + } bool Graphics::writeVRAM_16Colors(uint8_t x, uint8_t y, uint8_t character, uint8_t background, uint8_t foreground) { uint16_t cellOffset = static_cast(CONVERT_2D_1D(x, y, RawTextRenderer::CONSOLE_CHARS_H)) * 4; - cellOffset += m_vramStart; + if (!readFlag(tFlags::DoubleBufferingEnabled)) + cellOffset += m_16Color_currentFrameAddr; + else + cellOffset += m_16Color_secondFrameAddr; if (!m_videoMemory.w_Byte(cellOffset + tText16_CellStructure::character, character)) return false; //TODO: Error if (!m_videoMemory.w_Byte(cellOffset + tText16_CellStructure::background, background)) @@ -743,7 +771,7 @@ namespace dragon bool Graphics::clearVRAM_16Colors(uint8_t character, uint8_t background, uint8_t foreground) { - for (int32_t i = m_vramStart; i < m_vramStart + (RawTextRenderer::CONSOLE_CHARS_H * RawTextRenderer::CONSOLE_CHARS_V) * 4; i += 4) + for (int32_t i = m_16Color_currentFrameAddr; i < m_16Color_currentFrameAddr + m_16Color_frameSize; i += 4) { m_videoMemory.w_Byte(i + tText16_CellStructure::character, character); m_videoMemory.w_Byte(i + tText16_CellStructure::background, background); @@ -752,6 +780,25 @@ namespace dragon return true; } + void Graphics::swapBuffers_16Colors(void) + { + if (!readFlag(tFlags::DoubleBufferingEnabled)) + return; + for (int32_t i = m_16Color_currentFrameAddr, j = 0; i < m_16Color_currentFrameAddr + m_16Color_frameSize; i += 4, j += 4) + { + int8_t outByte = 0; + m_videoMemory.r_Byte(m_16Color_secondFrameAddr + j, outByte); + m_videoMemory.w_Byte(i + tText16_CellStructure::character, outByte); + m_videoMemory.r_Byte(m_16Color_secondFrameAddr + j + 1, outByte); + m_videoMemory.w_Byte(i + tText16_CellStructure::background, outByte); + m_videoMemory.r_Byte(m_16Color_secondFrameAddr + j + 2, outByte); + m_videoMemory.w_Byte(i + tText16_CellStructure::foreground, outByte); + } + uint16_t tmp = m_16Color_currentFrameAddr; + m_16Color_currentFrameAddr = m_16Color_secondFrameAddr; + m_16Color_secondFrameAddr = tmp; + } + diff --git a/src/hardware/VirtualIODevices.hpp b/src/hardware/VirtualIODevices.hpp index 8cf827d..e6fa3d0 100644 --- a/src/hardware/VirtualIODevices.hpp +++ b/src/hardware/VirtualIODevices.hpp @@ -358,6 +358,11 @@ namespace dragon inline static constexpr uint8_t background = 0x02; inline static constexpr uint8_t reserved = 0x03; }; + public: struct tFlags + { + inline static constexpr uint8_t DoubleBufferingEnabled = 0; + inline static constexpr uint8_t ScreenRedrawDisabled = 1; + }; public: Graphics(void); int8_t read8(uint16_t addr) override; @@ -365,18 +370,28 @@ namespace dragon int8_t write8(uint16_t addr, int8_t value) override; int16_t write16(uint16_t addr, int16_t value) override; + bool readFlag(uint8_t flg); + void setFlag(uint8_t flg, bool val = true); + ostd::ByteStream* getByteStream(void) override; inline uint16_t getVRAMStart(void) { return m_vramStart; } bool readVRAM_16Colors(uint8_t x, uint8_t y, tText16_Cell& outTextCell); bool writeVRAM_16Colors(uint8_t x, uint8_t y, uint8_t character = 0, uint8_t background = 0xFF, uint8_t foreground = 0xFF); bool clearVRAM_16Colors(uint8_t character = 0, uint8_t background = 0x00, uint8_t foreground = 0xFF); + void swapBuffers_16Colors(void); private: ostd::serial::SerialIO m_videoMemory; uint16_t m_vramStart { 0 }; uint8_t m_16Color_cellSize { 4 }; + uint16_t m_16Color_frameSize { 0 }; + uint16_t m_16Color_secondFrameAddr { 0 }; + uint16_t m_16Color_currentFrameAddr { 0 }; + bool m_16Color_doubleBufferingEnabled { false }; + + ostd::BitField_16 m_tempFlags; }; class SerialPort : public IMemoryDevice {