/* Copyright (c) 2021 Bad Diode Permission to use, copy, modify, and distribute this software for any purpose with or without fee is hereby granted, provided that the above copyright notice and this permission notice appear in all copies. THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE. */ #include #include #include "common.h" #include "filesystem.c" #include "uxn.c" #include "ppu.c" #include "apu.c" #include "file.c" #include "text.h" #include "rom.c" #include "config.c" #include "profiling.c" #include "devices.c" extern void uxn_eval_asm(u16 pc); // TODO: This should be on the IWRAM for maximum speed, as these are operations // we will use very often. extern u8 wst[256]; extern u8 rst[256]; extern u8 io_ports[256]; extern uintptr_t wst_ptr; extern uintptr_t rst_ptr; EWRAM_BSS u8 uxn_ram[KB(64)]; void init_uxn() { // Initialize uxn. u32 fill = 0; dma_fill(uxn_ram, fill, 0x10300, 3); // uxn_boot(u, uxn_ram, uxn_dei, uxn_deo); // Copy rom to VM. u8 uxn_rom[] = { // // ADD test. 0x80, 0x04, 0x80, 0x08, 0x18, // #04 #08 ADD -> 0c 0xa0, 0x00, 0x04, 0xa0, 0x00, 0x08, 0x38, // #0004 #0008 ADD2 -> 000c // SUB test. 0x80, 0x08, 0x80, 0x03, 0x19, // #08 #03 ADD -> 05 0xa0, 0x00, 0x08, 0xa0, 0x00, 0x03, 0x39, // #0008 #0003 ADD2 -> 0005 // MUL test. 0x80, 0x03, 0x80, 0x04, 0x1a, // #03 #04 MUL -> 0c 0xa0, 0x00, 0x03, 0xa0, 0x00, 0x04, 0x3a, // #0003 #0004 MUL2 -> 000c 0xa0, 0x00, 0xff, 0xa0, 0x00, 0x02, 0x3a, // #00ff #0002 MUL2 -> 01fe }; memcpy(uxn_ram + PAGE_PROGRAM, uxn_rom, sizeof(uxn_rom)); } int main(void) { // Adjust system wait times. SYSTEM_WAIT = SYSTEM_WAIT_CARTRIDGE; // Initialize filesystem. fs_init(); // Register interrupts. irq_init(); irs_set(IRQ_VBLANK, sound_vsync); // Initialize PPU. video_init(); // Initialize text engine. // #ifdef TEXT_ENABLE txt_init(1, TEXT_LAYER); txt_position(0,0); // #endif // Initialize UXN. init_uxn(); // Enable sound. init_sound(); // Main loop. // uxn_eval(&u, PAGE_PROGRAM); u8 frame_counter = 0; // NOTE: A VBLANK is 83776 cycles, anything other than that will make it so // we fail to render at 60FPS. // TODO: Initialize memory. // Initialize stack. for (size_t i = 0; i < 256; i++) { wst[i] = 0; rst[i] = 0; io_ports[i] = 0; } txt_printf("ROM"); for (size_t i = 0; i < 64; i++) { if (i % 8 == 0) { txt_printf("\n"); } txt_printf("%02x ", uxn_ram[i + PAGE_PROGRAM]); } txt_printf("\n\n"); uxn_eval_asm(PAGE_PROGRAM); txt_printf("STACK ("); txt_printf("PTR: %d)", wst_ptr - (uintptr_t)wst); for (size_t i = 0; i < 64; i++) { if (i % 8 == 0) { txt_printf("\n"); } txt_printf("%02x ", wst[i]); } uintptr_t stack_size = wst_ptr - (uintptr_t)wst; while(true) { txt_position(0,0); // bios_vblank_wait(); // FRAME_START(); // // PROF(handle_input(&u), input_cycles); // // PROF(uxn_eval(&u, PEEK2(&u.dev[0x20])), eval_cycles); // // PROF(sound_mix(), mix_cycles); // // // TODO: allow configuration to do VSYNC at 15 or 30 fps to avoid too // // // much memory copying on demanding uxn roms. // // PROF_SHOW(); // // PROF(flipbuf(), flip_cycles); // // frame_counter++; // // if (frame_counter == 60) { // // seconds++; // // frame_counter = 0; // // } // FRAME_END(); bios_vblank_wait(); FRAME_START(); flipbuf(); // screen_fill(0); // txt_printf("WST: 0x%08x\n", wst); // txt_printf("PTR: 0x%08x\n", wst_ptr); FRAME_END(); PROF_SHOW(); // txt_render(); // txt_clear(); } return 0; }