├── CMakeLists.txt ├── LICENSE ├── Makefile ├── README.md ├── TODO.txt ├── build ├── Makefile ├── wxWabbitemu.make └── wxWidgetsVer.make ├── core ├── alu.c ├── alu.h ├── control.c ├── control.h ├── core.c ├── core.h ├── coretypes.h ├── device.c ├── device.h ├── indexcb.c ├── indexcb.h └── optable.h ├── debugger ├── dbcommon.h ├── debuggerwindowclass.h ├── disassemble.c ├── disassemble.h ├── disassemblyview.cpp ├── disassemblyview.h ├── guidebug.cpp ├── guidebug.h └── panes │ ├── cpupane.cpp │ ├── cpupane.h │ ├── flagspane.cpp │ ├── flagspane.h │ ├── regpane.cpp │ └── regpane.h ├── gui ├── droptarget.cpp ├── droptarget.h ├── gui.cpp ├── gui.h ├── guiapp.cpp ├── guiapp.h ├── guilcd.cpp ├── guilcd.h ├── guiopenfile.cpp ├── guiopenfile.h ├── guisavestate.c ├── guisavestate.cpp ├── guiskinwindow.cpp ├── guiskinwindow.h ├── guivartree.cpp ├── guivartree.h ├── rom │ ├── Rom82.82p │ ├── Rom83.83p │ ├── Rom85.85s │ ├── Rom86.86p │ ├── bf73.h │ ├── bf73.hex │ ├── bf83p.h │ ├── bf83pbe.hex │ ├── bf83pse.h │ ├── bf83pse.hex │ ├── bf84p.h │ ├── bf84pbe.hex │ ├── bf84pse.h │ ├── bf84pse.hex │ └── rom8x.8xp ├── skins │ ├── TI-73.png │ ├── TI-82.png │ ├── TI-83+.png │ ├── TI-83+Keymap.png │ ├── TI-83+SE.png │ ├── TI-83.png │ ├── TI-83Keymap.png │ ├── ti-81.png │ ├── ti-81keymap.png │ ├── ti-82keymap.png │ ├── ti-84+.png │ ├── ti-84+se.png │ ├── ti-84+sekeymap.png │ ├── ti-85.png │ ├── ti-85Keymap.png │ ├── ti-86.png │ ├── ti-86keymap.png │ ├── ti73.h │ ├── ti81.h │ ├── ti82.h │ ├── ti83.h │ ├── ti83p.h │ ├── ti83pse.h │ ├── ti84p.h │ ├── ti84pse.h │ ├── ti85.h │ └── ti86.h ├── tiicons.h ├── wabbiticon.png ├── wabbiticon.xpm └── wizard │ ├── romwizard.cpp │ ├── romwizard.h │ ├── wizardcalctype.cpp │ ├── wizardcalctype.h │ ├── wizardos.cpp │ ├── wizardos.h │ ├── wizardstart.cpp │ └── wizardstart.h ├── hardware ├── 81hw.c ├── 81hw.h ├── 83hw.c ├── 83hw.h ├── 83phw.c ├── 83phw.h ├── 83psehw.c ├── 83psehw.h ├── 86hw.c ├── 86hw.h ├── keys.c ├── keys.h ├── lcd.c ├── lcd.h ├── link.c ├── link.h └── ti_stdint.h ├── interface ├── calc.c ├── calc.h ├── state.c └── state.h ├── makefile.old ├── meson.build ├── premake ├── Makefile ├── create_makefile.sh ├── premake4 ├── premake4.lua ├── premake4_linux_x86 └── use_wxwidgets.lua ├── res ├── break.bmp ├── goto.bmp ├── membreak.bmp ├── run.bmp ├── step.bmp ├── stepover.bmp ├── stop.bmp └── ti-icons.png ├── stdafx.h ├── utilities ├── bcalls.h ├── exportvar.c ├── exportvar.h ├── fileutilities.c ├── fileutilities.h ├── flags.h ├── gif.c ├── gif.h ├── gifhandle.c ├── gifhandle.h ├── label.c ├── label.h ├── print.c ├── print.h ├── savestate.c ├── savestate.h ├── sendfile.c ├── sendfile.h ├── sound.c ├── sound.h ├── types.h ├── var.c ├── var.h ├── zlibcmp.c └── zlibcmp.h └── z.rom /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Portions of this come from KiCad's CMakeLists.txt 2 | 3 | cmake_minimum_required(VERSION 3.0.2) 4 | 5 | # set the project name 6 | project(wxWabbitemu VERSION 0.1.0) 7 | 8 | # find wx + include it 9 | # Turn on wxWidgets compatibility mode for some classes 10 | add_definitions( -DWX_COMPATIBILITY ) 11 | 12 | # Don't link statically 13 | set( wxWidgets_CONFIG_OPTIONS ${wxWidgets_CONFIG_OPTIONS} --static=no ) 14 | 15 | # now hunt for wxWidgets 16 | # (adv is used for "advanced" widgets, such as the wizard) 17 | find_package(wxWidgets REQUIRED adv net core base) 18 | include(${wxWidgets_USE_FILE}) 19 | 20 | # mixing of C and C++ necessitates builds in c++ 21 | file(GLOB_RECURSE CFILES "${CMAKE_SOURCE_DIR}/*.c") 22 | SET_SOURCE_FILES_PROPERTIES(${CFILES} PROPERTIES LANGUAGE CXX ) 23 | 24 | # add the executable 25 | add_executable(wxWabbitemu 26 | #[[ Core ]] 27 | core/core.c 28 | core/alu.c 29 | core/control.c 30 | core/device.c 31 | core/indexcb.c 32 | 33 | #[[ Calc Interfacing ]] 34 | interface/calc.c 35 | interface/state.c 36 | 37 | #[[ Utilities/Libraries ]] 38 | utilities/exportvar.c 39 | utilities/fileutilities.c 40 | utilities/gif.c 41 | utilities/gifhandle.c 42 | utilities/label.c 43 | utilities/savestate.c 44 | utilities/sendfile.c 45 | utilities/var.c 46 | #[[ Hardware Emulation ]] 47 | hardware/81hw.c 48 | hardware/83hw.c 49 | hardware/83phw.c 50 | hardware/83psehw.c 51 | hardware/86hw.c 52 | hardware/keys.c 53 | hardware/lcd.c 54 | hardware/link.c 55 | #[[ wxWidgets GUI ]] 56 | gui/gui.cpp #[[ This requires gui/gui.h ]] 57 | gui/guiapp.cpp #[[ This requires gui/guiapp.h ]] 58 | gui/guiskinwindow.cpp #[[ This requires gui/guiskinwindow.h ]] 59 | gui/guilcd.cpp #[[ This requires gui/guilcd.h ]] 60 | gui/guivartree.cpp #[[ This requires gui/guivartree.h ]] 61 | gui/droptarget.cpp #[[ This requires gui/droptarget.h ]] 62 | gui/wizard/wizardstart.cpp #[[ This requires gui/wizard/wizardstart.h ]] 63 | gui/wizard/wizardcalctype.cpp #[[ This requires gui/wizard/wizardcalctype.h ]] 64 | gui/wizard/wizardos.cpp #[[ This requires gui/wizard/wizardos.h ]] 65 | gui/wizard/romwizard.cpp #[[ This requires gui/wizard/romwizard.h ]] 66 | debugger/guidebug.cpp #[[ This requires debugger/guidebug.h ]] 67 | #[[ Debugger and debugger GUI ]] 68 | debugger/disassemblyview.cpp #[[ This requires debugger/disassemblyview.h ]] 69 | debugger/disassemble.c 70 | debugger/panes/regpane.cpp #[[ This requires debugger/panes/regpane.h ]] 71 | debugger/panes/flagspane.cpp #[[ This requires debugger/panes/flagspane.h ]] 72 | debugger/panes/cpupane.cpp #[[ This requires debugger/panes/cpupane.h ]] 73 | ) 74 | 75 | target_include_directories(wxWabbitemu PUBLIC 76 | "${PROJECT_BINARY_DIR}" 77 | "${PROJECT_SOURCE_DIR}" 78 | "${PROJECT_SOURCE_DIR}/core" 79 | "${PROJECT_SOURCE_DIR}/debugger" 80 | "${PROJECT_SOURCE_DIR}/gui" 81 | "${PROJECT_SOURCE_DIR}/hardware" 82 | "${PROJECT_SOURCE_DIR}/interface" 83 | "${PROJECT_SOURCE_DIR}/utilities" 84 | ) 85 | 86 | target_link_libraries(wxWabbitemu ${wxWidgets_LIBRARIES}) 87 | 88 | add_definitions(-DHIGH_SHADE_GIF -DVERBOSE -D_LINUX -DWXVER) 89 | 90 | # Enable Unicode 91 | if( CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang" ) 92 | if( GCC_VERSION VERSION_EQUAL 4.8.0 OR GCC_VERSION VERSION_GREATER 4.8.0 ) 93 | add_definitions(-D_UNICODE) 94 | endif() 95 | endif() 96 | 97 | # CPack for packaging 98 | if( UNIX AND NOT APPLE ) 99 | 100 | # Create a *.deb file: 101 | set( CPACK_GENERATOR "DEB" ) 102 | set( CPACK_DEBIAN_PACKAGE_MAINTAINER "https://github.com/alberthdev/wxwabbitemu" ) 103 | 104 | set( CPACK_PACKAGE_VERSION_MAJOR 0 ) 105 | set( CPACK_PACKAGE_VERSION_MINOR 1 ) 106 | set( CPACK_PACKAGE_VERSION_PATCH 0 ) 107 | set( CPACK_PACKAGE_CONTACT Albert Huang ) 108 | set( CPACK_PACKAGE_DESCRIPTION_SUMMARY "wxWabbitemu built by CMake build system." ) 109 | 110 | include( CPack ) 111 | 112 | endif() 113 | 114 | install(TARGETS wxWabbitemu DESTINATION bin) 115 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | wxWabbitemu - a cross-platform TI-8x emulator based on Wabbitemu 2 | Copyright (C) 2016 Albert Huang + Chris Shappell 3 | Copyright (C) 2015 Revolution Software 4 | (with Spencer Putt, Don Straney, Chris Shappell, and James Montelongo) 5 | 6 | This program is free software; you can redistribute it and/or 7 | modify it under the terms of the GNU General Public License 8 | as published by the Free Software Foundation; either version 2 9 | of the License, or (at your option) any later version. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | # Quick reference: 2 | # @ silences the line 3 | # - ignores errors on the line 4 | 5 | PREFIX = $(DESTDIR)/usr/local 6 | BINDIR = $(PREFIX)/bin 7 | 8 | .PHONY: all help install uninstall distclean distclean-real 9 | 10 | # Wildcard rule 11 | .DEFAULT: 12 | @$(MAKE) -s -C premake 13 | $(MAKE) -C build $@ 14 | 15 | all: bin/wxWabbitemu 16 | 17 | bin/wxWabbitemu: 18 | @$(MAKE) wxWabbitemu 19 | 20 | help: 21 | @$(MAKE) -s -C build help 22 | @echo "" 23 | @echo "ADDITIONAL TARGETS:" 24 | @echo " install" 25 | @echo " uninstall" 26 | @echo " distclean" 27 | 28 | install: bin/wxWabbitemu 29 | @echo "Installing wxWabbitemu to: $(BINDIR)" 30 | install bin/wxWabbitemu $(BINDIR) 31 | 32 | uninstall: 33 | @echo "Uninstalling wxWabbitemu from: $(BINDIR)" 34 | rm -f $(BINDIR)/wxWabbitemu 35 | 36 | clean: 37 | $(MAKE) -C build clean 38 | -if [ -d build/obj ];then rmdir build/obj; fi 39 | -if [ -d bin ]; then rmdir bin; fi 40 | 41 | distclean: 42 | @echo "WARNING: Running distclean will require you to regenerate" 43 | @echo "your makefiles with Premake. Only do this if you suspect" 44 | @echo "that the Makefiles are corrupt." 45 | @echo "" 46 | @echo "Run make distclean-real to actually distclean." 47 | 48 | distclean-real: clean 49 | $(MAKE) -C premake distclean 50 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | wxWabbitemu 2 | ============ 3 | 4 | What is wxWabbitemu? 5 | --------------------- 6 | wxWabbitemu is a TI-8x emulator that uses the wxWidgets toolkit. 7 | It is based on a decent TI-8x emulator, Wabbitemu. 8 | Hence the name: wxWabbitemu! 9 | 10 | It is designed to mainly run on Linux, but it can be run on other 11 | platforms as well. 12 | 13 | wxWabbitemu supports loading any TI-8x variables, programs, apps, etc. 14 | It also supports loading and saving calculator states, capturing 15 | screenshots, debugging programs, and much more! 16 | 17 | wxWabbitemu History 18 | -------------------- 19 | This project was originally started by [Albert Huang (alberthdev)][albert] 20 | as an attempt to port a good TI-8x emulator to Linux. 21 | 22 | (At the time, there was TilEm, a GTK+ TI-8X emulator, but it was buggy, 23 | slow, and rarely updated.**) 24 | 25 | Thankfully, a Wabbitemu developer, [Chris Shappel (Buckeye)][buckeye], 26 | joined in to do most of the porting. Later, [David Gomes][dgomes] joined 27 | development and helped develop the GUI. 28 | 29 | Nowadays, these contributers are part of the project: 30 | 31 | * [Jon "Jonimus" Storm][jonimus] 32 | * [geekboy][geekboy] 33 | 34 | ** TilEm2: 35 | 36 | At the time of writing, TilEm2, written by new developers 37 | Thibault "contra-sh" Duponchelle and Benjamin "FloppusMaximus" Moody, 38 | was released. 39 | 40 | This version sports new emulation code, skinning support, and many 41 | improvements. If you find that wxWabbitemu is causing you too many 42 | problems, development/bug fixes are too slow, and/or you want to play 43 | with something new, give their emulator a try! 44 | 45 | http://lpg.ticalc.org/prj_tilem/ 46 | 47 | Installing wxWabbitemu 48 | ---------------------- 49 | wxWabbitemu can be found in the [eeems-linux](https://repo.eeems.codes/) pacman repository for arch based systems. Otherwise you will need to build it from source. 50 | 51 | Building wxWabbitemu 52 | --------------------- 53 | You need the following: 54 | 55 | * A working C compiler. This includes, but is not limited to, 56 | GCC and Clang. 57 | 58 | * The wxWidgets development files. Basically, the headers and linking 59 | libraries for wxWidgets. And of course, the wxWidgets library 60 | itself. 61 | 62 | * The GNU Make program. This program will build wxWabbitemu for you. 63 | BSD make might work as well, but no guarantees. 64 | 65 | In all of the commands that you are instructed to type in, you should 66 | follow each command with pressing the return key. 67 | 68 | **Install Dependencies:** 69 | 70 | * Debian, Ubuntu, Mint Linux, and friends: 71 | 72 | Run: 73 | 74 | sudo apt-get update && sudo apt-get upgrade 75 | 76 | Reboot if necessary. 77 | 78 | Then open a terminal again (if you rebooted), and type: 79 | 80 | # If libwxgtk3.0-dev isn't available, try libwxgtk2.8-dev. 81 | # 2.8 is available on older distros, while 3.0 is available 82 | # on more recent releases. 83 | # Also, on later Ubuntu releases you will need to use libgtk3.0-gtk3-dev 84 | sudo apt-get install build-essential libwxgtk3.0-dev 85 | 86 | * Fedora, RHEL, and friends: 87 | 88 | Run: 89 | 90 | su -c "yum update" 91 | 92 | Reboot if necessary. 93 | 94 | Then open a terminal again (if you rebooted), and type: 95 | 96 | su -c "yum install gcc gcc-c++ make wxGTK wxGTK-devel" 97 | 98 | Once you have installed the dependencies, you can go ahead and 99 | build wxWabbitemu! 100 | 101 | **Build wxWabbitemu:** 102 | 103 | In a terminal type: 104 | 105 | make 106 | 107 | **Run wxWabbitemu:** 108 | 109 | To run it, type: 110 | 111 | ./bin/wxWabbitemu 112 | 113 | Note, though, that wxwabbitemu is a portable file and it can be copied 114 | to anywhere in your computer and ran from any location. 115 | 116 | **Install wxWabbitemu:** 117 | 118 | To install, you can type: 119 | 120 | make install 121 | 122 | Make sure you do this as root. 123 | 124 | **Notes:** 125 | 126 | If you want to build on another platform, or use a different build 127 | system, you can use premake to generate a different file! In the premake 128 | directory, run the premake program (with the options you want) to create 129 | files that can build wxWabbitemu! 130 | 131 | (If you're running Linux x86, we've included the premake4 binary.) 132 | 133 | For more information and/or building instructions, visit the 134 | Building page on our website: 135 | 136 | https://github.com/alberthdev/wxwabbitemu/wiki/Building 137 | 138 | The End 139 | -------- 140 | That's it! We hope you enjoy wxWabbitemu! Should it fail to do 141 | something, or crash, please help us by reporting bugs in our 142 | issue tracker, located at https://github.com/alberthdev/wxwabbitemu/issues. 143 | 144 | License 145 | -------- 146 | See [LICENSE](License) 147 | 148 | [albert]: https://github.com/alberthdev 149 | [buckeye]: https://github.com/BuckeyeDude 150 | [dgomes]: https://github.com/davidgomes 151 | [jonimus]: https://github.com/Jonimoose 152 | [geekboy]: https://github.com/geekbozu 153 | -------------------------------------------------------------------------------- /TODO.txt: -------------------------------------------------------------------------------- 1 | TODO 2 | ===== 3 | Updated: 06/13/2012 4 | Update this date whenever changes are made! 5 | 6 | This is a non-exculsive TODO list for wxWabbitemu. 7 | This is a "take and work on it" kind of thing, so don't worry 8 | about time constraints for implementing these features! ;) 9 | 10 | This file is best viewed in a text editor with monospaced 11 | font (also known as fixed width font - examples include 12 | Courier New). 13 | 14 | If you are appending to this list, follow this format: 15 | = Feature/things 16 | ++++ Suggested by: username/name 17 | ++++ Rationale: why does this need to be implemented? 18 | ++++ Who's working on it: username/name working on it, as well 19 | ++++ as suggestions on who could do it 20 | ++++ Implementor's notes: notes by the implementor 21 | 22 | Separate them into a new line if they get too long, and indent 23 | with spaces to the end of the colon+space. 24 | 25 | That said, here are the things to be done: 26 | 27 | = Debugger 28 | ++++ Suggested by: alberthdev 29 | ++++ Rationale: meet the current featureset of Wabbitemu 30 | ++++ Who's working on it: Buckeye, but may need support of other people to 31 | finish the port 32 | ++++ Implementor's notes: N/A 33 | 34 | = Sound 35 | ++++ Suggested by: alberthdev 36 | ++++ Rationale: meet the current featureset of Wabbitemu 37 | ++++ Who's working on it: Nobody 38 | ++++ Implementor's notes: N/A 39 | 40 | = Linking 41 | ++++ Suggested by: alberthdev 42 | ++++ Rationale: meet the current featureset of Wabbitemu 43 | ++++ Who's working on it: Nobody 44 | ++++ Implementor's notes: N/A 45 | 46 | = Wabbitemu shared library 47 | ++++ Suggested by: alberthdev 48 | ++++ Rationale: Allow developers to include Wabbitemu in a library for 49 | ++++ their own use in their app. Code from here will probably 50 | ++++ be copied back to the original Wabbitemu project, since 51 | ++++ demand for such a library exists! ;) 52 | ++++ Who's working on it: Nobody 53 | ++++ Implementor's notes: N/A 54 | 55 | = Control emulated calculator with real calculator 56 | ++++ Suggested by: alberthdev 57 | ++++ Rationale: Allow users to use their real calculator to control 58 | ++++ instead of using a mouse or keyboard. This will need 59 | ++++ a LOT of help from ASM devs, TiLP devs. and others. 60 | ++++ It may be possible to simply use a bit of remote8x code. 61 | ++++ Who's working on it: Nobody 62 | ++++ Implementor's notes: N/A 63 | 64 | = ?? (add more stuff here!) 65 | -------------------------------------------------------------------------------- /build/Makefile: -------------------------------------------------------------------------------- 1 | # GNU Make solution makefile autogenerated by Premake 2 | # Type "make help" for usage help 3 | 4 | ifndef config 5 | config=debug 6 | endif 7 | export config 8 | 9 | PROJECTS := wxWabbitemu 10 | 11 | .PHONY: all clean help $(PROJECTS) 12 | 13 | all: $(PROJECTS) 14 | 15 | wxWabbitemu: 16 | @echo "==== Building wxWabbitemu ($(config)) ====" 17 | @${MAKE} --no-print-directory -C . -f wxWabbitemu.make 18 | 19 | clean: 20 | @${MAKE} --no-print-directory -C . -f wxWabbitemu.make clean 21 | 22 | help: 23 | @echo "Usage: make [config=name] [target]" 24 | @echo "" 25 | @echo "CONFIGURATIONS:" 26 | @echo " debug" 27 | @echo " release" 28 | @echo "" 29 | @echo "TARGETS:" 30 | @echo " all (default)" 31 | @echo " clean" 32 | @echo " wxWabbitemu" 33 | @echo "" 34 | @echo "For more information, see http://industriousone.com/premake/quick-start" 35 | -------------------------------------------------------------------------------- /build/wxWabbitemu.make: -------------------------------------------------------------------------------- 1 | # NOTE - this file has been modified to allow building with 2.8 and 3.0 2 | # Regenerating the Makefile will overwrite this change! 3 | 4 | include wxWidgetsVer.make 5 | 6 | # End patch by patch_makefile.sh (patched on Tue Aug 30 00:50:14 EDT 2016) 7 | 8 | # GNU Make project makefile autogenerated by Premake 9 | ifndef config 10 | config=debug 11 | endif 12 | 13 | ifndef verbose 14 | SILENT = @ 15 | endif 16 | 17 | ifndef CC 18 | CC = gcc 19 | endif 20 | 21 | ifndef CXX 22 | CXX = g++ 23 | endif 24 | 25 | ifndef AR 26 | AR = ar 27 | endif 28 | 29 | ifeq ($(config),debug) 30 | OBJDIR = obj/Debug 31 | TARGETDIR = ../bin 32 | TARGET = $(TARGETDIR)/wxWabbitemu 33 | DEFINES += -DDEBUG -D_UNICODE -DWXUSINGDLL -DHIGH_SHADE_GIF -DVERBOSE -D_LINUX -DWXVER 34 | INCLUDES += -I.. -I../core -I../debugger -I../gui -I../hardware -I../interface -I../utilities 35 | CPPFLAGS += -MMD -MP $(DEFINES) $(INCLUDES) 36 | CFLAGS += $(CPPFLAGS) $(ARCH) -g -Wall -x c++ $(WX_CFLAGS) 37 | CXXFLAGS += $(CFLAGS) 38 | LDFLAGS += $(WX_LDFLAGS) 39 | LIBS += 40 | RESFLAGS += $(DEFINES) $(INCLUDES) 41 | LDDEPS += 42 | LINKCMD = $(CXX) -o $(TARGET) $(OBJECTS) $(LDFLAGS) $(RESOURCES) $(ARCH) $(LIBS) 43 | define PREBUILDCMDS 44 | endef 45 | define PRELINKCMDS 46 | endef 47 | define POSTBUILDCMDS 48 | endef 49 | endif 50 | 51 | ifeq ($(config),release) 52 | OBJDIR = obj/Release 53 | TARGETDIR = ../bin 54 | TARGET = $(TARGETDIR)/wxWabbitemu 55 | DEFINES += -D_UNICODE -DWXUSINGDLL -DHIGH_SHADE_GIF -DVERBOSE -D_LINUX -DWXVER 56 | INCLUDES += -I.. -I../core -I../debugger -I../gui -I../hardware -I../interface -I../utilities 57 | CPPFLAGS += -MMD -MP $(DEFINES) $(INCLUDES) 58 | CFLAGS += $(CPPFLAGS) $(ARCH) -O2 -x c++ $(WX_CFLAGS) 59 | CXXFLAGS += $(CFLAGS) 60 | LDFLAGS += -s $(WX_LDFLAGS) 61 | LIBS += 62 | RESFLAGS += $(DEFINES) $(INCLUDES) 63 | LDDEPS += 64 | LINKCMD = $(CXX) -o $(TARGET) $(OBJECTS) $(LDFLAGS) $(RESOURCES) $(ARCH) $(LIBS) 65 | define PREBUILDCMDS 66 | endef 67 | define PRELINKCMDS 68 | endef 69 | define POSTBUILDCMDS 70 | endef 71 | endif 72 | 73 | OBJECTS := \ 74 | $(OBJDIR)/core.o \ 75 | $(OBJDIR)/alu.o \ 76 | $(OBJDIR)/control.o \ 77 | $(OBJDIR)/device.o \ 78 | $(OBJDIR)/indexcb.o \ 79 | $(OBJDIR)/calc.o \ 80 | $(OBJDIR)/state.o \ 81 | $(OBJDIR)/exportvar.o \ 82 | $(OBJDIR)/fileutilities.o \ 83 | $(OBJDIR)/gif.o \ 84 | $(OBJDIR)/gifhandle.o \ 85 | $(OBJDIR)/label.o \ 86 | $(OBJDIR)/savestate.o \ 87 | $(OBJDIR)/sendfile.o \ 88 | $(OBJDIR)/var.o \ 89 | $(OBJDIR)/81hw.o \ 90 | $(OBJDIR)/83hw.o \ 91 | $(OBJDIR)/83phw.o \ 92 | $(OBJDIR)/83psehw.o \ 93 | $(OBJDIR)/86hw.o \ 94 | $(OBJDIR)/keys.o \ 95 | $(OBJDIR)/lcd.o \ 96 | $(OBJDIR)/link.o \ 97 | $(OBJDIR)/gui.o \ 98 | $(OBJDIR)/guiapp.o \ 99 | $(OBJDIR)/guiskinwindow.o \ 100 | $(OBJDIR)/guilcd.o \ 101 | $(OBJDIR)/guivartree.o \ 102 | $(OBJDIR)/droptarget.o \ 103 | $(OBJDIR)/wizardstart.o \ 104 | $(OBJDIR)/wizardcalctype.o \ 105 | $(OBJDIR)/wizardos.o \ 106 | $(OBJDIR)/romwizard.o \ 107 | $(OBJDIR)/guidebug.o \ 108 | $(OBJDIR)/disassemblyview.o \ 109 | $(OBJDIR)/disassemble.o \ 110 | $(OBJDIR)/regpane.o \ 111 | $(OBJDIR)/flagspane.o \ 112 | $(OBJDIR)/cpupane.o \ 113 | 114 | RESOURCES := \ 115 | 116 | SHELLTYPE := msdos 117 | ifeq (,$(ComSpec)$(COMSPEC)) 118 | SHELLTYPE := posix 119 | endif 120 | ifeq (/bin,$(findstring /bin,$(SHELL))) 121 | SHELLTYPE := posix 122 | endif 123 | 124 | .PHONY: clean prebuild prelink 125 | 126 | all: $(TARGETDIR) $(OBJDIR) prebuild prelink $(TARGET) 127 | @: 128 | 129 | $(TARGET): $(GCH) $(OBJECTS) $(LDDEPS) $(RESOURCES) 130 | @echo Linking wxWabbitemu 131 | $(SILENT) $(LINKCMD) 132 | $(POSTBUILDCMDS) 133 | 134 | $(TARGETDIR): 135 | @echo Creating $(TARGETDIR) 136 | ifeq (posix,$(SHELLTYPE)) 137 | $(SILENT) mkdir -p $(TARGETDIR) 138 | else 139 | $(SILENT) mkdir $(subst /,\\,$(TARGETDIR)) 140 | endif 141 | 142 | $(OBJDIR): 143 | @echo Creating $(OBJDIR) 144 | ifeq (posix,$(SHELLTYPE)) 145 | $(SILENT) mkdir -p $(OBJDIR) 146 | else 147 | $(SILENT) mkdir $(subst /,\\,$(OBJDIR)) 148 | endif 149 | 150 | clean: 151 | @echo Cleaning wxWabbitemu 152 | ifeq (posix,$(SHELLTYPE)) 153 | $(SILENT) rm -f $(TARGET) 154 | $(SILENT) rm -rf $(OBJDIR) 155 | else 156 | $(SILENT) if exist $(subst /,\\,$(TARGET)) del $(subst /,\\,$(TARGET)) 157 | $(SILENT) if exist $(subst /,\\,$(OBJDIR)) rmdir /s /q $(subst /,\\,$(OBJDIR)) 158 | endif 159 | 160 | prebuild: 161 | $(PREBUILDCMDS) 162 | 163 | prelink: 164 | $(PRELINKCMDS) 165 | 166 | ifneq (,$(PCH)) 167 | $(GCH): $(PCH) 168 | @echo $(notdir $<) 169 | -$(SILENT) cp $< $(OBJDIR) 170 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 171 | endif 172 | 173 | $(OBJDIR)/core.o: ../core/core.c 174 | @echo $(notdir $<) 175 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 176 | $(OBJDIR)/alu.o: ../core/alu.c 177 | @echo $(notdir $<) 178 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 179 | $(OBJDIR)/control.o: ../core/control.c 180 | @echo $(notdir $<) 181 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 182 | $(OBJDIR)/device.o: ../core/device.c 183 | @echo $(notdir $<) 184 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 185 | $(OBJDIR)/indexcb.o: ../core/indexcb.c 186 | @echo $(notdir $<) 187 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 188 | $(OBJDIR)/calc.o: ../interface/calc.c 189 | @echo $(notdir $<) 190 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 191 | $(OBJDIR)/state.o: ../interface/state.c 192 | @echo $(notdir $<) 193 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 194 | $(OBJDIR)/exportvar.o: ../utilities/exportvar.c 195 | @echo $(notdir $<) 196 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 197 | $(OBJDIR)/fileutilities.o: ../utilities/fileutilities.c 198 | @echo $(notdir $<) 199 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 200 | $(OBJDIR)/gif.o: ../utilities/gif.c 201 | @echo $(notdir $<) 202 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 203 | $(OBJDIR)/gifhandle.o: ../utilities/gifhandle.c 204 | @echo $(notdir $<) 205 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 206 | $(OBJDIR)/label.o: ../utilities/label.c 207 | @echo $(notdir $<) 208 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 209 | $(OBJDIR)/savestate.o: ../utilities/savestate.c 210 | @echo $(notdir $<) 211 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 212 | $(OBJDIR)/sendfile.o: ../utilities/sendfile.c 213 | @echo $(notdir $<) 214 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 215 | $(OBJDIR)/var.o: ../utilities/var.c 216 | @echo $(notdir $<) 217 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 218 | $(OBJDIR)/81hw.o: ../hardware/81hw.c 219 | @echo $(notdir $<) 220 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 221 | $(OBJDIR)/83hw.o: ../hardware/83hw.c 222 | @echo $(notdir $<) 223 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 224 | $(OBJDIR)/83phw.o: ../hardware/83phw.c 225 | @echo $(notdir $<) 226 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 227 | $(OBJDIR)/83psehw.o: ../hardware/83psehw.c 228 | @echo $(notdir $<) 229 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 230 | $(OBJDIR)/86hw.o: ../hardware/86hw.c 231 | @echo $(notdir $<) 232 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 233 | $(OBJDIR)/keys.o: ../hardware/keys.c 234 | @echo $(notdir $<) 235 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 236 | $(OBJDIR)/lcd.o: ../hardware/lcd.c 237 | @echo $(notdir $<) 238 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 239 | $(OBJDIR)/link.o: ../hardware/link.c 240 | @echo $(notdir $<) 241 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 242 | $(OBJDIR)/gui.o: ../gui/gui.cpp 243 | @echo $(notdir $<) 244 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 245 | $(OBJDIR)/guiapp.o: ../gui/guiapp.cpp 246 | @echo $(notdir $<) 247 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 248 | $(OBJDIR)/guiskinwindow.o: ../gui/guiskinwindow.cpp 249 | @echo $(notdir $<) 250 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 251 | $(OBJDIR)/guilcd.o: ../gui/guilcd.cpp 252 | @echo $(notdir $<) 253 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 254 | $(OBJDIR)/guivartree.o: ../gui/guivartree.cpp 255 | @echo $(notdir $<) 256 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 257 | $(OBJDIR)/droptarget.o: ../gui/droptarget.cpp 258 | @echo $(notdir $<) 259 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 260 | $(OBJDIR)/wizardstart.o: ../gui/wizard/wizardstart.cpp 261 | @echo $(notdir $<) 262 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 263 | $(OBJDIR)/wizardcalctype.o: ../gui/wizard/wizardcalctype.cpp 264 | @echo $(notdir $<) 265 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 266 | $(OBJDIR)/wizardos.o: ../gui/wizard/wizardos.cpp 267 | @echo $(notdir $<) 268 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 269 | $(OBJDIR)/romwizard.o: ../gui/wizard/romwizard.cpp 270 | @echo $(notdir $<) 271 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 272 | $(OBJDIR)/guidebug.o: ../debugger/guidebug.cpp 273 | @echo $(notdir $<) 274 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 275 | $(OBJDIR)/disassemblyview.o: ../debugger/disassemblyview.cpp 276 | @echo $(notdir $<) 277 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 278 | $(OBJDIR)/disassemble.o: ../debugger/disassemble.c 279 | @echo $(notdir $<) 280 | $(SILENT) $(CC) $(CFLAGS) -o "$@" -c "$<" 281 | $(OBJDIR)/regpane.o: ../debugger/panes/regpane.cpp 282 | @echo $(notdir $<) 283 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 284 | $(OBJDIR)/flagspane.o: ../debugger/panes/flagspane.cpp 285 | @echo $(notdir $<) 286 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 287 | $(OBJDIR)/cpupane.o: ../debugger/panes/cpupane.cpp 288 | @echo $(notdir $<) 289 | $(SILENT) $(CXX) $(CXXFLAGS) -o "$@" -c "$<" 290 | 291 | -include $(OBJECTS:%.o=%.d) 292 | -------------------------------------------------------------------------------- /build/wxWidgetsVer.make: -------------------------------------------------------------------------------- 1 | # Modified wxWidgets environment setter to allow both 3.0 and 2.8 2 | # versions to build 3 | WX_CFLAGS = `wx-config --unicode=yes --version=3.0 --cxxflags 2>/dev/null || wx-config --unicode=yes --version=2.8 --cxxflags 2>/dev/null` 4 | WX_LDFLAGS = `wx-config --unicode=yes --version=3.0 --libs richtext,aui,xrc,qa,html,adv,core,xml,net 2>/dev/null || wx-config --unicode=yes --version=2.8 --libs richtext,aui,xrc,qa,html,adv,core,xml,net 2>/dev/null` 5 | -------------------------------------------------------------------------------- /core/alu.h: -------------------------------------------------------------------------------- 1 | #ifndef ALU_H 2 | #define ALU_H 3 | 4 | #define SIGN_MASK 0x80 5 | #define ZERO_MASK 0x40 6 | #define X5_MASK 0x20 7 | #define HC_MASK 0x10 8 | #define X3_MASK 0x08 9 | #define PV_MASK 0x04 10 | #define N_MASK 0x02 11 | #define CARRY_MASK 0x01 12 | 13 | #define unaffect( mask ) ((cpu->f)&(mask)) 14 | 15 | #define dosign( tval ) (( tval )?SIGN_MASK:0) 16 | #define dozero( tval ) (( tval )?ZERO_MASK:0) 17 | #define dox5( tval ) (( tval )?X5_MASK:0) 18 | #define dohc( tval ) (( tval )?HC_MASK:0) 19 | #define dox3( tval ) (( tval )?X3_MASK:0) 20 | #define doparity( tval ) (( tval )?PV_MASK:0) 21 | #define dooverflow( tval ) (( tval )?PV_MASK:0) 22 | #define ADD_INSTR 0 23 | #define SUB_INSTR N_MASK 24 | #define carry( tval ) (( tval )?CARRY_MASK:0) 25 | 26 | #define signchk( tval ) ((tval)&0x80) 27 | #define zerochk( zchk ) dozero( (((zchk)&0xFF)==0) ) 28 | #define x5chk( tval ) ((tval)&0x20) 29 | #define hcaddchk( opr1 , opr2 , carry) ((((opr1)&0x0F)+((opr2)&0x0F) + carry)&0x10) 30 | #define hcsubchk( opr1 , opr2 , carry) ((((opr1)&0x0F)-((opr2)&0x0F) - carry)&0x10) 31 | #define x3chk( tval ) ((tval)&0x08) 32 | #define vchkadd(opr1,opr2,res) ( ((((opr1) & 0x80) == ((opr2) & 0x80) ) & (((opr1) & 0x80) != ((res) & 0x80))) << 2) 33 | #define vchksub(opr1,opr2,res) ( ((((opr1) & 0x80) != ((opr2) & 0x80) ) & (((opr1) & 0x80) != ((res) & 0x80))) << 2) 34 | #define parity( opr1 ) ((((((opr1)>>0)^((opr1)>>1)^((opr1)>>2)^((opr1)>>3)^((opr1)>>4)^((opr1)>>5)^((opr1)>>6)^((opr1)>>7))&1)^1)*PV_MASK) 35 | //add or sub 36 | #define carrychk(tval) (((tval) & 0x100) >> 8) 37 | 38 | 39 | #define signchk16( tval ) (((tval)>>8)&0x80) 40 | #define zerochk16( tval ) dozero(((tval)&0xFFFF)==0) 41 | #define x5chk16( tval ) (((tval)>>8)&0x20) 42 | #define hcaddchk16( opr1 , opr2 , carry) (((((opr1)&0xfff)+((opr2)&0xfff)+(carry))&0x1000)>>8) 43 | #define hcsubchk16( opr1 , opr2 , carry) (((((opr1)&0xfff)-((opr2)&0xfff)-(carry))&0x1000)>>8) 44 | #define x3chk16( tval ) (((tval)>>8)&8) 45 | #define vchkadd16(opr1,opr2,res) ( ((((opr1) & 0x8000) == ((opr2) & 0x8000) ) & (((opr1) & 0x8000) != ((res) & 0x8000))) << 2) 46 | #define vchksub16(opr1,opr2,res) ( ((((opr1) & 0x8000) != ((opr2) & 0x8000) ) & (((opr1) & 0x8000) != ((res) & 0x8000))) << 2) 47 | //add sub 48 | #define carrychk16(tval) (((tval) & 0x10000) >> 16) 49 | 50 | void add_a_num8(CPU_t*); 51 | void adc_a_num8(CPU_t*); 52 | void sub_a_num8(CPU_t*); 53 | void sbc_a_num8(CPU_t*); 54 | void adc_a_reg8(CPU_t *); 55 | void add_a_reg8(CPU_t *); 56 | void sbc_a_reg8(CPU_t *); 57 | void sub_a_reg8(CPU_t *); 58 | void dec_reg8(CPU_t *); 59 | void inc_reg8(CPU_t *); 60 | 61 | 62 | void dec_reg16(CPU_t *); 63 | void inc_reg16(CPU_t *); 64 | void add_hl_reg16(CPU_t *); 65 | void adc_hl_reg16(CPU_t *); 66 | void sbc_hl_reg16(CPU_t *); 67 | 68 | void and_reg8(CPU_t *); 69 | void and_num8(CPU_t *); 70 | 71 | void cp_reg8(CPU_t *); 72 | void cp_num8(CPU_t *); 73 | void cpd(CPU_t *); 74 | void cpdr(CPU_t *); 75 | void cpi(CPU_t *); 76 | void cpir(CPU_t *); 77 | 78 | 79 | void cpl(CPU_t *); 80 | void daa(CPU_t *); 81 | 82 | 83 | void or_reg8(CPU_t *); 84 | void or_num8(CPU_t *); 85 | 86 | void xor_num8(CPU_t *); 87 | void xor_reg8(CPU_t *); 88 | 89 | void rlca(CPU_t *); 90 | void rla(CPU_t *); 91 | void rrca(CPU_t *); 92 | void rra(CPU_t *); 93 | 94 | void rld(CPU_t *); 95 | void rrd(CPU_t *); 96 | 97 | //CB opcodes 98 | 99 | void bit(CPU_t *); 100 | void res(CPU_t *); 101 | void set(CPU_t *); 102 | void rl_reg(CPU_t *); 103 | void rlc_reg(CPU_t *); 104 | void rr_reg(CPU_t *); 105 | void rrc_reg(CPU_t *); 106 | 107 | void srl_reg(CPU_t *); 108 | void sra_reg(CPU_t *); 109 | void sla_reg(CPU_t *); 110 | void sll_reg(CPU_t *); 111 | #endif 112 | -------------------------------------------------------------------------------- /core/control.h: -------------------------------------------------------------------------------- 1 | #ifndef CONTROL_H 2 | #define CONTROL_H 3 | 4 | #include "core.h" 5 | 6 | void rst(CPU_t *); 7 | void ret(CPU_t *); 8 | void out(CPU_t *); 9 | void in(CPU_t *); 10 | void call(CPU_t *); 11 | void call_condition(CPU_t *); 12 | void push_reg16(CPU_t *); 13 | void pop_reg16(CPU_t *); 14 | void ld_sp_hl(CPU_t *); 15 | void ld_mem16_hlf(CPU_t *); 16 | void ld_hlf_mem16(CPU_t *); 17 | void ld_hl_num16(CPU_t *); 18 | void ld_de_num16(CPU_t *); 19 | void ld_bc_num16(CPU_t *); 20 | void ld_sp_num16(CPU_t *); 21 | void ld_a_mem16(CPU_t *); 22 | void ld_a_bc(CPU_t *); 23 | void ld_a_de(CPU_t *); 24 | void ld_mem16_a(CPU_t *); 25 | void ld_bc_a(CPU_t *); 26 | void ld_de_a(CPU_t *); 27 | void ld_r_num8(CPU_t *); 28 | void ld_r_r(CPU_t *); 29 | void halt(CPU_t *); 30 | void ex_sp_hl(CPU_t *); 31 | void ex_de_hl(CPU_t *); 32 | void exx(CPU_t *); 33 | void ex_af_afp(CPU_t *); 34 | void jp_hl(CPU_t *); 35 | void jp(CPU_t *); 36 | void jr(CPU_t *); 37 | void jp_condition(CPU_t *); 38 | void jr_condition(CPU_t *); 39 | void djnz(CPU_t *); 40 | void ret_condition(CPU_t *); 41 | void ccf(CPU_t *); 42 | void scf(CPU_t *); 43 | 44 | 45 | void IM0(CPU_t *); 46 | void IM1(CPU_t *); 47 | void IM2(CPU_t *); 48 | void ei(CPU_t *); 49 | void di(CPU_t *); 50 | void ldd(CPU_t *); 51 | void lddr(CPU_t *); 52 | void ldi(CPU_t *); 53 | void ldir(CPU_t *); 54 | void neg(CPU_t *); 55 | void nop(CPU_t *); 56 | void ld_mem16_reg16(CPU_t *); 57 | void ld_reg16_mem16(CPU_t *); 58 | void in_reg_c(CPU_t *); 59 | void ind(CPU_t *); 60 | void indr(CPU_t *); 61 | void ini(CPU_t *); 62 | void inir(CPU_t *); 63 | void ld_i_a(CPU_t *); 64 | void ld_r_a(CPU_t *); 65 | void ld_a_i(CPU_t *); 66 | void ld_a_r(CPU_t *); 67 | void out_reg(CPU_t *); 68 | void outd(CPU_t *); 69 | void otdr(CPU_t *); 70 | void outi(CPU_t *); 71 | void otir(CPU_t *); 72 | void reti(CPU_t *); 73 | void retn(CPU_t *); 74 | void ednop(CPU_t *); 75 | 76 | 77 | #endif 78 | -------------------------------------------------------------------------------- /core/coretypes.h: -------------------------------------------------------------------------------- 1 | #ifndef CORETYPES_H_ 2 | #define CORETYPES_H_ 3 | 4 | #define NumElm(array) (sizeof (array) / sizeof ((array)[0])) 5 | 6 | #include 7 | 8 | #ifndef _WINDOWS 9 | #ifndef _LINUX 10 | typedef char TCHAR; 11 | typedef const char *LPCTSTR; 12 | #endif 13 | typedef void *LPVOID; 14 | typedef intptr_t INT_PTR; 15 | typedef uint8_t BYTE, *LPBYTE; 16 | typedef uint16_t WORD, *LPWORD; 17 | typedef uint32_t DWORD, *LPDWORD; 18 | 19 | #ifndef MAX_PATH 20 | #define MAX_PATH 256 21 | #endif 22 | #endif 23 | 24 | #ifdef WINVER 25 | typedef int BOOL; 26 | #else 27 | #ifndef OBJC_BOOL_DEFINED 28 | typedef signed char BOOL; 29 | #endif 30 | #endif 31 | 32 | #ifndef TRUE 33 | #define FALSE (0) 34 | #define TRUE (!FALSE) 35 | #endif 36 | 37 | #endif /*CORETYPES_H_*/ 38 | -------------------------------------------------------------------------------- /core/device.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #include "device.h" 4 | 5 | #ifdef DEBUG 6 | void console_output(CPU_t *cpu, device_t *dev) { 7 | if (cpu->output) { 8 | printf("output byte: %d\n",cpu->bus); 9 | cpu->output = FALSE; 10 | } 11 | } 12 | #endif 13 | 14 | void ClearDevices(CPU_t* cpu) { 15 | int i; 16 | for (i = 0; i < ARRAYSIZE(cpu->pio.interrupt); i++) { 17 | cpu->pio.devices[i].active = FALSE; 18 | interrupt_t *intVal = &cpu->pio.interrupt[i]; 19 | intVal->interrupt_val = -1; 20 | intVal->skip_factor = 1; 21 | intVal->skip_count = 0; 22 | } 23 | cpu->pio.num_interrupt = 0; 24 | } 25 | 26 | int device_output(CPU_t *cpu, unsigned char dev) { 27 | if (cpu->pio.devices[dev].active) { 28 | cpu->output = TRUE; 29 | if (!cpu->pio.devices[dev].protected_port || !cpu->mem_c->flash_locked) 30 | cpu->pio.devices[dev].code(cpu, &(cpu->pio.devices[dev])); 31 | if (cpu->pio.devices[dev].breakpoint) 32 | cpu->pio.breakpoint_callback(cpu, &(cpu->pio.devices[dev])); 33 | if (cpu->output) { 34 | /* Device is not responding */ 35 | cpu->output = FALSE; 36 | return 1; 37 | } 38 | } 39 | return 0; 40 | } 41 | 42 | int device_input(CPU_t *cpu, unsigned char dev) { 43 | if (cpu->pio.devices[dev].active) { 44 | cpu->input = TRUE; 45 | if (cpu->pio.devices[dev].breakpoint) 46 | cpu->pio.breakpoint_callback(cpu, &(cpu->pio.devices[dev])); 47 | cpu->pio.devices[dev].code(cpu, &(cpu->pio.devices[dev])); 48 | if (cpu->input) { 49 | /* Device is not responding */ 50 | cpu->input = FALSE; 51 | cpu->bus = 0xFF; 52 | return 1; 53 | } 54 | } else { 55 | cpu->bus = 0xFF; 56 | return 1; 57 | } 58 | return 0; 59 | } 60 | 61 | void Append_interrupt_device(CPU_t *cpu, int port, int skip) { 62 | interrupt_t *intVal = &cpu->pio.interrupt[cpu->pio.num_interrupt]; 63 | intVal->interrupt_val = port; 64 | intVal->skip_factor = skip; 65 | cpu->pio.num_interrupt++; 66 | } 67 | 68 | void Modify_interrupt_device(CPU_t *cpu, int port, int skip) { 69 | for(int i = 0; i < cpu->pio.num_interrupt; i++) { 70 | if (cpu->pio.interrupt[i].interrupt_val == port) { 71 | cpu->pio.interrupt[i].skip_factor = skip; 72 | break; 73 | } 74 | } 75 | } 76 | 77 | int device_control(CPU_t *cpu, unsigned char dev) { 78 | device_t *device = &cpu->pio.devices[dev]; 79 | if (device->active) { 80 | device->code(cpu, device); 81 | } 82 | return 0; 83 | } 84 | 85 | -------------------------------------------------------------------------------- /core/device.h: -------------------------------------------------------------------------------- 1 | #ifndef DEVICE_H 2 | #define DEVICE_H 3 | #include "core.h" 4 | 5 | #define DEV_INDEX(zdev) (zdev - cpu->pio.devices) 6 | 7 | int device_output(CPU_t *, unsigned char); 8 | int device_input(CPU_t *, unsigned char); 9 | int device_control(CPU_t *cpu, unsigned char dev); 10 | void Append_interrupt_device(CPU_t *, int, int); 11 | void Modify_interrupt_device(CPU_t *, int, int); 12 | void ClearDevices(CPU_t*); 13 | #endif 14 | -------------------------------------------------------------------------------- /core/indexcb.h: -------------------------------------------------------------------------------- 1 | #include "core.h" 2 | #include "alu.h" 3 | #include "control.h" 4 | 5 | void bit_ind(CPU_t*, char); 6 | void res_ind(CPU_t*, char); 7 | void set_ind(CPU_t*, char); 8 | 9 | void rr_ind(CPU_t*, char); 10 | void rrc_ind(CPU_t*, char); 11 | void rl_ind(CPU_t*, char); 12 | void rlc_ind(CPU_t*, char); 13 | 14 | void srl_ind(CPU_t*, char); 15 | void sll_ind(CPU_t*, char); 16 | 17 | void sra_ind(CPU_t*, char); 18 | void sla_ind(CPU_t*, char); 19 | -------------------------------------------------------------------------------- /debugger/dbcommon.h: -------------------------------------------------------------------------------- 1 | #ifndef DBCOMMON_H 2 | #define DBCOMMON_H 3 | 4 | #include "calc.h" 5 | 6 | typedef enum { 7 | HEX2, 8 | HEX4, 9 | FLOAT2, 10 | FLOAT4, 11 | DEC3, 12 | DEC5, 13 | BIN8, 14 | BIN16, 15 | CHAR1, 16 | } VALUE_FORMAT; 17 | 18 | typedef enum { 19 | HEX, 20 | DEC, 21 | BIN, 22 | } DISPLAY_BASE; 23 | 24 | typedef enum { 25 | REGULAR, //view paged memory 26 | FLASH, //view all flash pages 27 | RAM, //view all ram pages 28 | } ViewType; 29 | 30 | typedef struct { 31 | int total; 32 | BOOL state[32]; 33 | } ep_state; 34 | 35 | #endif /* DBCOMMON_H */ 36 | -------------------------------------------------------------------------------- /debugger/debuggerwindowclass.h: -------------------------------------------------------------------------------- 1 | #ifndef DEBUGGERWINDOWCLASS_H 2 | #define DEBUGGERWINDOWCLASS_H 3 | 4 | class DebuggerWindowClass { 5 | public: 6 | virtual void DebugUpdateWindow() = 0; 7 | 8 | }; 9 | 10 | #endif -------------------------------------------------------------------------------- /debugger/disassemble.h: -------------------------------------------------------------------------------- 1 | #ifndef DISASSEMBLE_H 2 | #define DISASSEMBLE_H 3 | #include "stdafx.h" 4 | 5 | #include "core.h" 6 | #include "dbcommon.h" 7 | 8 | #define DA_NOP 0 9 | #define DA_EX_AF_AF_ 1 10 | #define DA_DJNZ_X 2 11 | #define DA_JR_X 3 12 | #define DA_JR_CC_X 4 13 | #define DA_LD_RP_X 5 14 | #define DA_ADD_HL_RP 6 15 | #define DA_LD__BC__A 7 16 | #define DA_LD_A__BC_ 8 17 | #define DA_LD__DE__A 9 18 | #define DA_LD_A__DE_ 10 19 | #define DA_LD__X__HL 11 20 | #define DA_LD_HL__X_ 12 21 | #define DA_LD__X__A 13 22 | #define DA_LD_A__X_ 14 23 | #define DA_INC_RP 15 24 | #define DA_DEC_RP 16 25 | #define DA_INC_R 17 26 | #define DA_DEC_R 18 27 | #define DA_LD_R_X 19 28 | #define DA_RLCA 20 29 | #define DA_RRCA 21 30 | #define DA_RLA 22 31 | #define DA_RRA 23 32 | #define DA_DAA 24 33 | #define DA_CPL 25 34 | #define DA_SCF 26 35 | #define DA_CCF 27 36 | #define DA_LD_R_R 28 37 | #define DA_HALT 29 38 | #define DA_ALU 30 39 | #define DA_ALU_A 31 40 | #define DA_RET_CC 32 41 | #define DA_POP_RP 33 42 | #define DA_RET 34 43 | #define DA_EXX 35 44 | #define DA_JP_HL 36 45 | #define DA_LD_SP_HL 37 46 | #define DA_JP_CC_X 38 47 | #define DA_JP_X 39 48 | #define DA_OUT__X__A 40 49 | #define DA_IN_A__X_ 41 50 | #define DA_EX__SP__HL 42 51 | #define DA_EX_DE_HL 43 52 | #define DA_DI 44 53 | #define DA_EI 45 54 | #define DA_CALL_CC_X 46 55 | #define DA_PUSH_RP 47 56 | #define DA_CALL_X 48 57 | #define DA_ALU_X 49 58 | #define DA_ALU_A_X 50 59 | #define DA_RST_X 51 60 | #define DA_ROT 52 61 | #define DA_BIT 53 62 | #define DA_RES 54 63 | #define DA_SET 55 64 | #define DA_IN_R__C_ 56 65 | #define DA_OUT__C__R 57 66 | #define DA_SBC_HL_RP 58 67 | #define DA_ADC_HL_RP 59 68 | #define DA_LD__X__RP 60 69 | #define DA_LD_RP__X_ 61 70 | #define DA_NEG 62 71 | #define DA_RETN 63 72 | #define DA_RETI 64 73 | #define DA_IM_X 65 74 | #define DA_LD_I_A 66 75 | #define DA_LD_R_A 67 76 | #define DA_LD_A_I 68 77 | #define DA_LD_A_R 69 78 | #define DA_RRD 70 79 | #define DA_RLD 71 80 | #define DA_NOP_ED 72 81 | #define DA_BLI 73 82 | #define DA_ROT_R 74 83 | #define DA_BIT_R 75 84 | #define DA_RES_R 76 85 | #define DA_SET_R 77 86 | #define DA_ROT_I 78 87 | #define DA_BIT_I 79 88 | #define DA_RES_I 80 89 | #define DA_SET_I 81 90 | #define DA_ADD_RI_RP 82 91 | #define DA_LD_RI__X_ 83 92 | #define DA_LD__X__RI 84 93 | #define DA_INC_RI 85 94 | #define DA_DEC_RI 86 95 | #define DA_LD_RI_X 87 96 | #define DA_LD_RI_R 88 97 | #define DA_LD_R_RI 89 98 | #define DA_ALU_RI 90 99 | #define DA_ALU_A_RI 91 100 | #define DA_JP_RI 92 101 | #define DA_LD_SP_RI 93 102 | #define DA_EX__SP__RI 94 103 | #define DA_LABEL 95 104 | #define DA_BCALL 96 105 | #define DA_BCALL_N 97 106 | #define DA_BIT_RF 98 107 | #define DA_RES_RF 99 108 | #define DA_SET_RF 100 109 | #define DA_BIT_IF 101 110 | #define DA_RES_IF 102 111 | #define DA_SET_IF 103 112 | #define DA_BJUMP 104 113 | #define DA_BJUMP_N 105 114 | #define DA_LD__HL__X DA_BJUMP_N + 1 115 | #define DA_LD__HL__R DA_LD__HL__X + 1 116 | #define DA_LD_R__HL_ DA_LD__HL__R 117 | #define DA_INC__HL_ DA_LD_R__HL_ + 1 118 | #define DA_DEC__HL_ DA_INC__HL_ + 1 119 | #define DA_BIT__HL_ DA_DEC__HL_ + 1 120 | #define DA_RES__HL_ DA_BIT__HL_ + 1 121 | #define DA_SET__HL_ DA_RES__HL_ + 1 122 | 123 | 124 | typedef struct Z80_info { 125 | int index; 126 | union { 127 | struct { 128 | INT_PTR a1, a2, a3, a4; 129 | }; 130 | INT_PTR a[4]; 131 | }; 132 | int size; /* Size of command */ 133 | waddr_t waddr; 134 | TCHAR expanded[32]; 135 | } Z80_info_t; 136 | 137 | typedef struct Z80_command { 138 | TCHAR format[32]; /* printf formatted string */ 139 | TCHAR clocks; /* clocks to complete */ 140 | TCHAR clocks_cond; /* Conditional clocks to complete */ 141 | #ifdef da_ready 142 | TCHAR flag_effects[8]; /* Flag effects for all 8 bits */ 143 | TCHAR *flag_description; /* optional description of flag effects */ 144 | #endif 145 | } Z80_com_t; 146 | 147 | int disassemble(LPCALC lpCalc, ViewType type, waddr_t waddr, int count, Z80_info_t *result); 148 | waddr_t GetNextAddr(memory_context_t *memc, ViewType type, waddr_t waddr); 149 | waddr_t OffsetWaddr(memory_context_t *memc, ViewType type, waddr_t waddr, int offset); 150 | 151 | 152 | #endif /* #ifndef DISASSEMBLE_H */ 153 | -------------------------------------------------------------------------------- /debugger/disassemblyview.cpp: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | #include "disassemblyview.h" 3 | #include "calc.h" 4 | 5 | extern Z80_com_t da_opcode[256]; 6 | 7 | int DisassemblyView::FindLastItem() { 8 | bool doneBank0 = false; 9 | int i; 10 | for (i = 0; i < 0xFFFF; i++) { 11 | if (!doneBank0 && (zinf[i].waddr.addr >> 14) == 1) { 12 | doneBank0 = true; 13 | } 14 | if (doneBank0 && (zinf[i].waddr.addr >> 14) == 0) { 15 | break; 16 | } 17 | } 18 | return i; 19 | } 20 | 21 | DisassemblyView::DisassemblyView(wxWindow *parent, LPCALC lpCalc, ViewType type): 22 | wxListCtrl(parent,wxID_ANY, wxDefaultPosition, wxDefaultSize, wxLC_REPORT|wxLC_VIRTUAL){ 23 | this->lpCalc = lpCalc; 24 | this->viewType = type; 25 | wxListItem col0; 26 | col0.SetId(0); 27 | col0.SetText( _T("Address") ); 28 | col0.SetWidth(70); 29 | InsertColumn(0, col0); 30 | 31 | wxListItem col1; 32 | col1.SetId(1); 33 | col1.SetText( _T("Data") ); 34 | col1.SetWidth(77); 35 | InsertColumn(1, col1); 36 | 37 | wxListItem col2; 38 | col2.SetId(2); 39 | col2.SetText( _T("Disassembly") ); 40 | col2.SetWidth(315); 41 | InsertColumn(2, col2); 42 | 43 | wxListItem col3; 44 | col3.SetId(3); 45 | col3.SetText( _T("Size") ); 46 | col3.SetWidth(42); 47 | InsertColumn(3, col3); 48 | 49 | wxListItem col4; 50 | col4.SetId(4); 51 | col4.SetText( _T("Clocks") ); 52 | col4.SetWidth(56); 53 | InsertColumn(4, col4); 54 | 55 | zinf = new Z80_info_t[0xFFFF]; 56 | memset(zinf, 0, sizeof(Z80_info_t) * 0xFFFF); 57 | waddr_t waddr = addr_to_waddr(&lpCalc->mem_c, 0); 58 | disassemble(lpCalc, REGULAR, waddr, 0xFFFF, zinf); 59 | 60 | SetItemCount(FindLastItem()); 61 | } 62 | 63 | wxListItemAttr *DisassemblyView::OnGetItemAttr(long item) const { 64 | if (lpCalc->cpu.pc == zinf[item].waddr.addr) { 65 | wxColor pcColor; 66 | if (lpCalc->cpu.halt) { 67 | pcColor = wxColor(200, 200, 100); 68 | } else { 69 | pcColor = wxColor(180, 180, 180); 70 | } 71 | 72 | return new wxListItemAttr(*wxBLACK, pcColor, *wxNORMAL_FONT); 73 | } 74 | if (check_break(&lpCalc->mem_c, zinf[item].waddr)) { 75 | return new wxListItemAttr(*wxWHITE, wxColor(230, 160, 180), *wxNORMAL_FONT); 76 | } 77 | if (check_mem_write_break(&lpCalc->mem_c, zinf[item].waddr)) { 78 | return new wxListItemAttr(*wxWHITE, wxColor(255, 177, 100), *wxNORMAL_FONT); 79 | } 80 | if (check_mem_read_break(&lpCalc->mem_c, zinf[item].waddr)) { 81 | return new wxListItemAttr(*wxWHITE, wxColor(255, 250, 145), *wxNORMAL_FONT); 82 | } 83 | return wxListCtrl::OnGetItemAttr(item); 84 | } 85 | 86 | int DisassemblyView::MapAddressToIndex(waddr_t &waddr) { 87 | for (int i = 0; i < 0xFFFF; i++) { 88 | if (zinf[i].waddr.addr == waddr.addr && zinf[i].waddr.page == waddr.page && zinf[i].waddr.is_ram == waddr.is_ram) { 89 | return i; 90 | } 91 | if (zinf[i].waddr.addr > waddr.addr && zinf[i].waddr.page == waddr.page && zinf[i].waddr.is_ram == waddr.is_ram) { 92 | return i - 1; 93 | } 94 | } 95 | return -1; 96 | } 97 | 98 | waddr_t& DisassemblyView::MapIndexToAddress(int index) { 99 | return zinf[index].waddr; 100 | } 101 | 102 | void DisassemblyView::DebugUpdateWindow() { 103 | this->Refresh(); 104 | } 105 | 106 | void DisassemblyView::GotoAddress(waddr_t waddr) { 107 | int i = MapAddressToIndex(waddr); 108 | EnsureVisible(i); 109 | } 110 | 111 | wxString DisassemblyView::OnGetItemText(long item, long column) const{ 112 | TCHAR s[64]; 113 | memset(s, 0, sizeof(s)); 114 | switch (column) { 115 | case 0: 116 | sprint_addr(lpCalc, &zinf[item], s); 117 | break; 118 | case 1: 119 | sprint_data(lpCalc, &zinf[item], s); 120 | break; 121 | case 2: 122 | sprint_command(lpCalc, &zinf[item], s); 123 | break; 124 | case 3: 125 | sprint_size(lpCalc, &zinf[item], s); 126 | break; 127 | case 4: 128 | sprint_clocks(lpCalc, &zinf[item], s); 129 | break; 130 | } 131 | return wxString(s); 132 | } 133 | 134 | void DisassemblyView::sprint_addr(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const { 135 | int page = zinf->waddr.page; 136 | if (zinf->waddr.is_ram) { 137 | switch (lpCalc->cpu.pio.model) { 138 | case TI_83P: 139 | case TI_73: 140 | page += 0x40; 141 | break; 142 | case TI_83PSE: 143 | case TI_84P: 144 | case TI_84PSE: 145 | page += 0x80; 146 | break; 147 | } 148 | } 149 | _tprintf(s, _T("%02X %04X"), page, zinf->waddr.addr); 150 | } 151 | 152 | void DisassemblyView::sprint_data(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const { 153 | int j; 154 | 155 | if (zinf->size == 0) { 156 | return; 157 | } 158 | 159 | waddr_t waddr = zinf->waddr; 160 | for (j = 0; j < zinf->size; j++) { 161 | waddr.addr = zinf->waddr.addr + j; 162 | if (waddr.addr % PAGE_SIZE < zinf->waddr.addr % PAGE_SIZE) { 163 | waddr.page++; 164 | //we don't handle ram changes here because things should never cross pages 165 | //therefore i don't really care 166 | } 167 | _tprintf(s + (j*2), _T("%02x"), wmem_read(lpCalc->cpu.mem_c, waddr)); 168 | } 169 | } 170 | 171 | void DisassemblyView::sprint_command(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const { 172 | _tcscpy(s, zinf->expanded); 173 | } 174 | 175 | void DisassemblyView::sprint_size(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const { 176 | if (zinf->size == 0) { 177 | return; 178 | } 179 | _tprintf(s, _T("%d"), zinf->size); 180 | } 181 | 182 | void DisassemblyView::sprint_clocks(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const { 183 | if (da_opcode[zinf->index].clocks != -1) { 184 | if (da_opcode[zinf->index].clocks_cond) { 185 | _tprintf(s, _T("%d/%d"), da_opcode[zinf->index].clocks, da_opcode[zinf->index].clocks_cond); 186 | } else { 187 | _tprintf(s, _T("%d"), da_opcode[zinf->index].clocks); 188 | } 189 | } else { 190 | *s = '\0'; 191 | } 192 | } -------------------------------------------------------------------------------- /debugger/disassemblyview.h: -------------------------------------------------------------------------------- 1 | #ifndef DISASSEMBLYVIEW_H 2 | #define DISASSEMBLYVIEW_H 3 | #include 4 | #include 5 | #include "debuggerwindowclass.h" 6 | #include "disassemble.h" 7 | 8 | class DisassemblyView: public wxListCtrl, DebuggerWindowClass { 9 | public: 10 | DisassemblyView(wxWindow *parent, LPCALC lpCalc, ViewType type); 11 | wxString OnGetItemText(long item, long column) const; 12 | wxListItemAttr * OnGetItemAttr(long item) const; 13 | void GotoAddress(waddr_t waddr); 14 | ViewType viewType; 15 | waddr_t& MapIndexToAddress(int index); 16 | int MapAddressToIndex(waddr_t &address); 17 | 18 | void DebugUpdateWindow(); 19 | private: 20 | LPCALC lpCalc; 21 | void sprint_data(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const; 22 | void sprint_addr(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const; 23 | void sprint_command(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const; 24 | void sprint_size(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const; 25 | void sprint_clocks(LPCALC lpCalc, const Z80_info_t *zinf, TCHAR *s) const; 26 | int FindLastItem(); 27 | Z80_info_t *zinf; 28 | }; 29 | #endif -------------------------------------------------------------------------------- /debugger/guidebug.h: -------------------------------------------------------------------------------- 1 | #include "gui.h" 2 | #include "disassemblyview.h" 3 | #include "debuggerwindowclass.h" 4 | 5 | #include "panes/regpane.h" 6 | #include "panes/flagspane.h" 7 | #include "panes/cpupane.h" 8 | 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | #define wxDEBUGGERID 1 15 | 16 | /* TODO: 17 | * [21:07:24] alberthro at this point you need to do 4 things 18 | * [21:07:30] in this order 19 | * [21:08:25] 4. make a memory view 20 | * [21:08:49] at that point your debugger is adequate enough to solve 70% of problems 21 | * 22 | * We'll get there... eventually! :) 23 | */ 24 | 25 | class WabbitemuDebugger: public wxFrame, public DebuggerWindowClass 26 | { 27 | public: 28 | WabbitemuDebugger(WabbitemuFrame *windowMain, LPCALC lpCalc); 29 | void DebugUpdateWindow(); 30 | DECLARE_EVENT_TABLE() 31 | protected: 32 | wxSplitterWindow* m_splitter1; 33 | wxScrolledWindow* m_scrolledWindow1; 34 | DisassemblyView* m_disasmView; 35 | wxScrolledWindow* m_scrolledWindow6; 36 | wxPanel* m_disasmGotoPanel; 37 | wxButton* m_disasmGotoButton; 38 | wxBoxSizer* bSizer3; 39 | wxStaticText* m_staticText22; 40 | wxTextCtrl* m_disasmGotoText; 41 | wxNotebook* m_notebook1; 42 | wxNotebook* m_notebook2; 43 | wxScrolledWindow* m_scrolledWindow4; 44 | wxPanel* m_panel1; 45 | wxPanel* m_panel2; 46 | wxPanel* m_panel4; 47 | wxScrolledWindow* m_scrolledWindow14; 48 | wxToolBar* m_toolBar1; 49 | RegPane *regPane; 50 | FlagsPane *flagsPane; 51 | CPUPane *cpuPane; 52 | wxCollapsiblePane* interruptPane; 53 | wxCollapsiblePane* keyboardPane; 54 | wxCollapsiblePane* displayPane; 55 | 56 | private: 57 | LPCALC lpCalc; 58 | WabbitemuFrame *wabbitemuFrame; 59 | 60 | 61 | void OnClose(wxCloseEvent& event); 62 | void OnToolbarRun(wxCommandEvent & WXUNUSED(event)); 63 | void OnToolbarBreak(wxCommandEvent & WXUNUSED(event)); 64 | void OnToolbarMemBreak(wxCommandEvent & WXUNUSED(event)); 65 | void OnToolbarStep(wxCommandEvent & WXUNUSED(event)); 66 | void OnToolbarStepOver(wxCommandEvent & WXUNUSED(event)); 67 | void OnToolbarGoto(wxCommandEvent & WXUNUSED(event)); 68 | 69 | void OnDisasmGoto(wxCommandEvent & WXUNUSED(event)); 70 | void OnDisasmGotoEnter(wxCommandEvent & WXUNUSED(event)); 71 | 72 | void OnCollapsiblePaneChanged(wxCollapsiblePaneEvent &event); 73 | }; 74 | -------------------------------------------------------------------------------- /debugger/panes/cpupane.cpp: -------------------------------------------------------------------------------- 1 | #include "cpupane.h" 2 | #include "alu.h" 3 | #include "gui.h" 4 | #include 5 | 6 | enum 7 | { 8 | ID_Check_Halt, 9 | ID_Text_Freq, 10 | ID_Text_Bus 11 | 12 | }; 13 | 14 | BEGIN_EVENT_TABLE(CPUPane, wxCollapsiblePane) 15 | EVT_CHECKBOX(ID_Check_Halt, CPUPane::OnCheckChanged) 16 | EVT_TEXT_ENTER(ID_Text_Freq, CPUPane::OnFreqTextEnter) 17 | EVT_TEXT_ENTER(ID_Text_Bus, CPUPane::OnBusTextEnter) 18 | END_EVENT_TABLE() 19 | 20 | CPUPane::CPUPane(wxWindow *parent, DebuggerWindowClass *debugWindow, LPCALC lpCalc) : 21 | wxCollapsiblePane(parent, wxID_ANY, wxT("CPU Status"), wxDefaultPosition, wxDefaultSize, wxCP_NO_TLW_RESIZE | wxCP_DEFAULT_STYLE) 22 | { 23 | this->lpCalc = lpCalc; 24 | this->debugWindow = debugWindow; 25 | wxWindow *cpuPaneWindow = GetPane(); 26 | 27 | wxBoxSizer* bSizer27; 28 | bSizer27 = new wxBoxSizer( wxVERTICAL ); 29 | 30 | m_haltCheck = new wxCheckBox( cpuPaneWindow, ID_Check_Halt, wxT("Halt"), wxDefaultPosition, wxDefaultSize, 0 ); 31 | bSizer27->Add( m_haltCheck, 0, wxALL, 5 ); 32 | 33 | wxBoxSizer* bSizer28; 34 | bSizer28 = new wxBoxSizer( wxHORIZONTAL ); 35 | 36 | m_staticText23 = new wxStaticText( cpuPaneWindow, wxID_ANY, wxT("Freq"), wxDefaultPosition, wxDefaultSize, 0 ); 37 | m_staticText23->Wrap( -1 ); 38 | bSizer28->Add( m_staticText23, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 ); 39 | 40 | m_freqText = new wxTextCtrl( cpuPaneWindow, ID_Text_Freq, wxEmptyString, wxDefaultPosition, wxDefaultSize, wxTE_PROCESS_ENTER ); 41 | bSizer28->Add( m_freqText, 0, wxALL, 5 ); 42 | 43 | bSizer27->Add( bSizer28, 0, wxEXPAND, 5 ); 44 | 45 | wxBoxSizer* bSizer29; 46 | bSizer29 = new wxBoxSizer( wxHORIZONTAL ); 47 | 48 | m_staticText24 = new wxStaticText( cpuPaneWindow, wxID_ANY, wxT("Bus"), wxDefaultPosition, wxDefaultSize, 0 ); 49 | m_staticText24->Wrap( -1 ); 50 | bSizer29->Add( m_staticText24, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 ); 51 | 52 | m_busText = new wxTextCtrl( cpuPaneWindow, ID_Text_Bus, wxEmptyString, wxDefaultPosition, wxDefaultSize, wxTE_PROCESS_ENTER ); 53 | bSizer29->Add( m_busText, 0, wxALL, 5 ); 54 | 55 | bSizer27->Add( bSizer29, 0, wxEXPAND, 5 ); 56 | 57 | cpuPaneWindow->SetSizer( bSizer27 ); 58 | cpuPaneWindow->Layout(); 59 | bSizer27->Fit( cpuPaneWindow ); 60 | } 61 | 62 | void CPUPane::DebugUpdateWindow() { 63 | m_haltCheck->SetValue(lpCalc->cpu.halt); 64 | m_freqText->SetValue(wxString::Format(_T("%.2f"), lpCalc->timer_c.freq / 1000000.0)); 65 | m_busText->SetValue(wxString::Format(wxT("%02X"), lpCalc->cpu.bus)); 66 | } 67 | 68 | void CPUPane::OnFreqTextEnter(wxCommandEvent &event) { 69 | std::stringstream ss; 70 | ss << m_freqText->GetValue(); 71 | ss >> lpCalc->timer_c.freq; 72 | lpCalc->timer_c.freq *= 1000000; 73 | debugWindow->DebugUpdateWindow(); 74 | } 75 | 76 | void CPUPane::OnBusTextEnter(wxCommandEvent &event) { 77 | int output; 78 | std::stringstream ss; 79 | ss << std::hex << m_busText->GetValue(); 80 | ss >> output; 81 | lpCalc->cpu.bus = (unsigned char) output; 82 | debugWindow->DebugUpdateWindow(); 83 | } 84 | 85 | 86 | void CPUPane::OnCheckChanged(wxCommandEvent &event) { 87 | lpCalc->cpu.halt = !lpCalc->cpu.halt; 88 | debugWindow->DebugUpdateWindow(); 89 | } -------------------------------------------------------------------------------- /debugger/panes/cpupane.h: -------------------------------------------------------------------------------- 1 | #ifndef CPUPANE_H 2 | #define CPUPANE_H 3 | 4 | #include 5 | #include 6 | 7 | #include "calc.h" 8 | #include "debuggerwindowclass.h" 9 | 10 | class CPUPane : public wxCollapsiblePane, public DebuggerWindowClass { 11 | private: 12 | LPCALC lpCalc; 13 | wxCheckBox* m_haltCheck; 14 | wxStaticText* m_staticText23; 15 | wxTextCtrl* m_freqText; 16 | wxStaticText* m_staticText24; 17 | wxTextCtrl* m_busText; 18 | DebuggerWindowClass *debugWindow; 19 | 20 | void OnCheckChanged(wxCommandEvent &event); 21 | void OnFreqTextEnter(wxCommandEvent &event); 22 | void OnBusTextEnter(wxCommandEvent &event); 23 | protected: 24 | DECLARE_EVENT_TABLE() 25 | public: 26 | CPUPane(wxWindow *parent, DebuggerWindowClass *debugWindow, LPCALC lpCalc); 27 | void DebugUpdateWindow(); 28 | }; 29 | 30 | #endif -------------------------------------------------------------------------------- /debugger/panes/flagspane.cpp: -------------------------------------------------------------------------------- 1 | #include "flagspane.h" 2 | #include "alu.h" 3 | 4 | enum 5 | { 6 | ID_Radio_Z, 7 | ID_Radio_C, 8 | ID_Radio_S, 9 | ID_Radio_PV, 10 | ID_Radio_HC, 11 | ID_Radio_N 12 | }; 13 | 14 | BEGIN_EVENT_TABLE(FlagsPane, wxCollapsiblePane) 15 | EVT_CHECKBOX(wxID_ANY, FlagsPane::OnCheckChanged) 16 | END_EVENT_TABLE() 17 | 18 | FlagsPane::FlagsPane(wxWindow *parent, DebuggerWindowClass *debugWindow, LPCALC lpCalc) : 19 | wxCollapsiblePane(parent, wxID_ANY, wxT("Flags"), wxDefaultPosition, wxDefaultSize, wxCP_NO_TLW_RESIZE | wxCP_DEFAULT_STYLE) 20 | { 21 | this->lpCalc = lpCalc; 22 | 23 | wxWindow *flagsPaneWindow = GetPane(); 24 | this->debugWindow = debugWindow; 25 | 26 | wxGridSizer* gSizer5; 27 | gSizer5 = new wxGridSizer( 2, 3, 0, 0 ); 28 | 29 | m_zCheck = new wxCheckBox( flagsPaneWindow, ID_Radio_Z, wxT("z"), wxDefaultPosition, wxDefaultSize, 0 ); 30 | gSizer5->Add( m_zCheck, 0, wxALL, 5 ); 31 | 32 | m_cCheck = new wxCheckBox( flagsPaneWindow, ID_Radio_C, wxT("c"), wxDefaultPosition, wxDefaultSize, 0 ); 33 | gSizer5->Add( m_cCheck, 0, wxALL, 5 ); 34 | 35 | m_sCheck = new wxCheckBox( flagsPaneWindow, ID_Radio_S, wxT("s"), wxDefaultPosition, wxDefaultSize, 0 ); 36 | gSizer5->Add( m_sCheck, 0, wxALL, 5 ); 37 | 38 | m_pvCheck = new wxCheckBox( flagsPaneWindow, ID_Radio_PV, wxT("p/v"), wxDefaultPosition, wxDefaultSize, 0 ); 39 | gSizer5->Add( m_pvCheck, 0, wxALL, 5 ); 40 | 41 | m_hcCheck = new wxCheckBox( flagsPaneWindow, ID_Radio_HC, wxT("hc"), wxDefaultPosition, wxDefaultSize, 0 ); 42 | gSizer5->Add( m_hcCheck, 0, wxALL, 5 ); 43 | 44 | m_nCheck = new wxCheckBox( flagsPaneWindow, ID_Radio_N, wxT("n"), wxDefaultPosition, wxDefaultSize, 0 ); 45 | gSizer5->Add( m_nCheck, 0, wxALL, 5 ); 46 | 47 | flagsPaneWindow->SetSizer( gSizer5 ); 48 | flagsPaneWindow->Layout(); 49 | 50 | flagsPaneWindow->SetSizer(gSizer5); 51 | flagsPaneWindow->Layout(); 52 | gSizer5->Fit( flagsPaneWindow ); 53 | } 54 | 55 | void FlagsPane::DebugUpdateWindow() { 56 | m_zCheck->SetValue((lpCalc->cpu.f & ZERO_MASK) != 0); 57 | m_cCheck->SetValue((lpCalc->cpu.f & CARRY_MASK) != 0); 58 | m_sCheck->SetValue((lpCalc->cpu.f & SIGN_MASK) != 0); 59 | m_pvCheck->SetValue((lpCalc->cpu.f & PV_MASK) != 0); 60 | m_hcCheck->SetValue((lpCalc->cpu.f & HC_MASK) != 0); 61 | m_nCheck->SetValue((lpCalc->cpu.f & N_MASK) != 0); 62 | } 63 | 64 | void FlagsPane::OnCheckChanged(wxCommandEvent &event) { 65 | switch (event.GetId()) { 66 | case ID_Radio_Z: 67 | lpCalc->cpu.f ^= ZERO_MASK; 68 | break; 69 | case ID_Radio_C: 70 | lpCalc->cpu.f ^= CARRY_MASK; 71 | break; 72 | case ID_Radio_S: 73 | lpCalc->cpu.f ^= SIGN_MASK; 74 | break; 75 | case ID_Radio_PV: 76 | lpCalc->cpu.f ^= PV_MASK; 77 | break; 78 | case ID_Radio_HC: 79 | lpCalc->cpu.f ^= HC_MASK; 80 | break; 81 | case ID_Radio_N: 82 | lpCalc->cpu.f ^= N_MASK; 83 | break; 84 | } 85 | debugWindow->DebugUpdateWindow(); 86 | } -------------------------------------------------------------------------------- /debugger/panes/flagspane.h: -------------------------------------------------------------------------------- 1 | #ifndef FLAGSPANE_H 2 | #define FLAGSPANE_H 3 | 4 | #include 5 | #include 6 | 7 | #include "calc.h" 8 | #include "debuggerwindowclass.h" 9 | 10 | class FlagsPane : public wxCollapsiblePane, public DebuggerWindowClass { 11 | private: 12 | LPCALC lpCalc; 13 | wxPanel* m_flagsPane; 14 | wxCheckBox* m_zCheck; 15 | wxCheckBox* m_cCheck; 16 | wxCheckBox* m_sCheck; 17 | wxCheckBox* m_pvCheck; 18 | wxCheckBox* m_hcCheck; 19 | wxCheckBox* m_nCheck; 20 | DebuggerWindowClass* debugWindow; 21 | 22 | void OnCheckChanged(wxCommandEvent &event); 23 | protected: 24 | DECLARE_EVENT_TABLE() 25 | public: 26 | FlagsPane(wxWindow *parent, DebuggerWindowClass *debugWindow, LPCALC lpCalc); 27 | void DebugUpdateWindow(); 28 | }; 29 | 30 | #endif -------------------------------------------------------------------------------- /debugger/panes/regpane.h: -------------------------------------------------------------------------------- 1 | #ifndef REGPANE_H 2 | #define REGPANE_H 3 | 4 | #include 5 | #include 6 | 7 | #include "calc.h" 8 | #include "debuggerwindowclass.h" 9 | 10 | class RegPane : public wxCollapsiblePane, public DebuggerWindowClass { 11 | private: 12 | wxTextCtrl* m_afText; 13 | wxTextCtrl* m_afpText; 14 | wxTextCtrl* m_bcText; 15 | wxTextCtrl* m_bcpText; 16 | wxTextCtrl* m_deText; 17 | wxTextCtrl* m_depText; 18 | wxTextCtrl* m_hlText; 19 | wxTextCtrl* m_hlpText; 20 | wxTextCtrl* m_ixText; 21 | wxTextCtrl* m_iyText; 22 | wxTextCtrl* m_pcText; 23 | wxTextCtrl* m_spText; 24 | LPCALC lpCalc; 25 | DebuggerWindowClass *debugWindow; 26 | 27 | void OnTextEntered(wxCommandEvent &event); 28 | protected: 29 | DECLARE_EVENT_TABLE() 30 | public: 31 | RegPane(wxWindow *parent, DebuggerWindowClass *debugWindow, LPCALC lpCalc); 32 | void DebugUpdateWindow(); 33 | }; 34 | 35 | #endif -------------------------------------------------------------------------------- /gui/droptarget.cpp: -------------------------------------------------------------------------------- 1 | #include "droptarget.h" 2 | #include "sendfile.h" 3 | #include "gui.h" 4 | 5 | bool DnDFile::OnDropFiles(wxCoord, wxCoord, const wxArrayString& filenames) 6 | { 7 | size_t nFiles = filenames.GetCount(); 8 | for (int i = 0; i < nFiles; i++ ) { 9 | SendFile(lpCalc, filenames[i].c_str(), SEND_CUR); 10 | } 11 | 12 | return true; 13 | } 14 | -------------------------------------------------------------------------------- /gui/droptarget.h: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include "calc.h" 5 | 6 | class DnDFile : public wxFileDropTarget 7 | { 8 | public: 9 | DnDFile(wxWindow *pOwner, LPCALC lpCalc) { m_pOwner = pOwner; this->lpCalc = lpCalc; } 10 | 11 | virtual bool OnDropFiles(wxCoord x, wxCoord y, const wxArrayString& filenames); 12 | 13 | private: 14 | LPCALC lpCalc; 15 | wxWindow *m_pOwner; 16 | }; 17 | -------------------------------------------------------------------------------- /gui/gui.h: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #ifndef GUI_WX_H 4 | #define GUI_WX_H 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | #if (wxUSE_UNICODE) 15 | #include 16 | #endif 17 | 18 | #include "guilcd.h" 19 | #include "guiskinwindow.h" 20 | #include "guivartree.h" 21 | #include "calc.h" 22 | 23 | enum 24 | { 25 | ID_LCD, 26 | }; 27 | 28 | class WabbitemuFrame: public wxFrame 29 | { 30 | public: 31 | WabbitemuFrame(LPCALC); 32 | wxWindow *wxLCD; 33 | 34 | void OnKeyDown(wxKeyEvent& event); 35 | void OnKeyUp(wxKeyEvent& event); 36 | void SetSpeed(int speed); 37 | int gui_draw(); 38 | void gui_frame_update(); 39 | void OnTimer(wxTimerEvent& event); 40 | protected: 41 | DECLARE_EVENT_TABLE() 42 | private: 43 | wxWindow *skinWindow; 44 | bool is_resizing; 45 | VarTree *varTree; 46 | //menu items 47 | void OnFileQuit(wxCommandEvent& event); 48 | void OnFileClose(wxCommandEvent& event); 49 | void OnFileSave(wxCommandEvent& event); 50 | void OnFileNew(wxCommandEvent& event); 51 | void OnFileOpen(wxCommandEvent& event); 52 | void OnFileGIF(wxCommandEvent& event); 53 | 54 | void OnViewSkin(wxCommandEvent& event); 55 | void OnViewVariables(wxCommandEvent& event); 56 | void OnPauseEmulation(wxCommandEvent& event); 57 | void OnTurnCalcOn(wxCommandEvent& event); 58 | 59 | void OnSetSpeed(wxCommandEvent& event); 60 | void OnSetSpeedCustom(wxCommandEvent& event); 61 | void OnSetSize(wxCommandEvent& event); 62 | 63 | void OnDebugReset(wxCommandEvent& event); 64 | void OnDebugOpen(wxCommandEvent& event); 65 | void OnDebugOn(wxCommandEvent& event); 66 | 67 | void OnHelpSetup(wxCommandEvent& event); 68 | void OnHelpWebsite(wxCommandEvent& event); 69 | void OnHelpAbout(wxCommandEvent& event); 70 | 71 | void OnPaint(wxPaintEvent& event); 72 | // Resize 73 | void OnResize(wxSizeEvent& event); 74 | void OnShow(wxShowEvent& event); 75 | 76 | // We use "isShownVar" instead of "isShown" because "isShown" is 77 | // an existing wxWidgets method 78 | int isShownVar = 0; 79 | 80 | LPCALC lpCalc; 81 | 82 | void OnLeftButtonDown(wxMouseEvent& event); 83 | void OnLeftButtonUp(wxMouseEvent& event); 84 | void OnSize(wxSizeEvent& event); 85 | void OnQuit(wxCloseEvent& event); 86 | void FinalizeButtons(); 87 | }; 88 | int SetGIFName(); 89 | void gui_debug(LPCALC lpCalc); 90 | WabbitemuFrame* gui_frame(LPCALC lpCalc); 91 | #endif 92 | -------------------------------------------------------------------------------- /gui/guiapp.cpp: -------------------------------------------------------------------------------- 1 | #include "guiapp.h" 2 | #include "gui.h" 3 | #include "wizard/romwizard.h" 4 | #include "sendfile.h" 5 | 6 | WabbitemuFrame *frames[MAX_CALCS]; 7 | 8 | BOOL WabbitemuApp::DoRomWizard() { 9 | RomWizard wizard; 10 | bool success = wizard.Begin(); 11 | return success; 12 | } 13 | 14 | void WabbitemuApp::LoadSettings(LPCALC lpCalc) 15 | { 16 | settingsConfig = new wxConfig(wxT("Wabbitemu")); 17 | wxString tempString; 18 | settingsConfig->Read(wxT("/rom_path"), &tempString, wxEmptyString); 19 | _tcscpy(lpCalc->rom_path, tempString.c_str()); 20 | settingsConfig->Read(wxT("/SkinEnabled"), &lpCalc->SkinEnabled, FALSE); 21 | } 22 | 23 | bool WabbitemuApp::OnInit() 24 | { 25 | wxImage::AddHandler(new wxPNGHandler); 26 | //stolen from the windows version 27 | ParseCommandLineArgs(); 28 | 29 | memset(frames, 0, sizeof(frames)); 30 | LPCALC lpCalc = calc_slot_new(); 31 | LoadSettings(lpCalc); 32 | 33 | WabbitemuFrame *frame; 34 | int result = rom_load(lpCalc, lpCalc->rom_path); 35 | if (result == TRUE) { 36 | frame = gui_frame(lpCalc); 37 | } else { 38 | calc_slot_free(lpCalc); 39 | BOOL loadedRom = FALSE; 40 | if (parsedArgs.num_rom_files > 0) { 41 | for (int i = 0; i < parsedArgs.num_rom_files; i++) { 42 | if (rom_load(lpCalc, parsedArgs.rom_files[i])) { 43 | gui_frame(lpCalc); 44 | loadedRom = TRUE; 45 | break; 46 | } 47 | } 48 | } 49 | if (!loadedRom) { 50 | bool success = DoRomWizard(); 51 | if (!success) { 52 | return FALSE; 53 | } 54 | } 55 | } 56 | LoadCommandlineFiles((INT_PTR) lpCalc, LoadToLPCALC); 57 | timer = new wxTimer(); 58 | timer->Connect(wxEVT_TIMER, (wxObjectEventFunction) &WabbitemuApp::OnTimer); 59 | timer->Start(TPF, false); 60 | return TRUE; 61 | } 62 | 63 | void WabbitemuApp::SaveSettings(LPCALC lpCalc) { 64 | #ifdef _UNICODE 65 | wxString rom_path(lpCalc->rom_path, wxConvUTF8); 66 | #else 67 | wxString rom_path(lpCalc->rom_path); 68 | #endif 69 | settingsConfig->Write(wxT("rom_path"), rom_path); 70 | settingsConfig->Write(wxT("SkinEnabled"), lpCalc->SkinEnabled); 71 | settingsConfig->Flush(); 72 | } 73 | 74 | int WabbitemuApp::OnExit() { 75 | SaveSettings(&calcs[0]); 76 | //load ROMs first 77 | for (int i = 0; i < parsedArgs.num_rom_files; i++) { 78 | free(parsedArgs.rom_files[i]); 79 | parsedArgs.rom_files[i] = NULL; 80 | } 81 | //then archived files 82 | for (int i = 0; i < parsedArgs.num_archive_files; i++) { 83 | free(parsedArgs.archive_files[i]); 84 | parsedArgs.archive_files[i] = NULL; 85 | } 86 | //then ram 87 | for (int i = 0; i < parsedArgs.num_ram_files; i++) { 88 | free(parsedArgs.ram_files[i]); 89 | parsedArgs.ram_files[i] = NULL; 90 | } 91 | //finally utility files (label, break, etc) 92 | for (int i = 0; i < parsedArgs.num_utility_files; i++) { 93 | free(parsedArgs.utility_files[i]); 94 | parsedArgs.utility_files[i] = NULL; 95 | } 96 | return 0; 97 | } 98 | 99 | 100 | unsigned WabbitemuApp::GetTickCount() 101 | { 102 | struct timeval tv; 103 | if(gettimeofday(&tv, NULL) != 0) 104 | return 0; 105 | 106 | return (tv.tv_sec * 1000) + (tv.tv_usec / 1000); 107 | } 108 | 109 | 110 | void WabbitemuApp::OnTimer(wxTimerEvent& event) { 111 | static int difference; 112 | static unsigned prevTimer; 113 | unsigned dwTimer = GetTickCount(); 114 | 115 | // How different the timer is from where it should be 116 | // guard from erroneous timer calls with an upper bound 117 | // that's the limit of time it will take before the 118 | // calc gives up and claims it lost time 119 | difference += ((dwTimer - prevTimer) & 0x003F) - TPF; 120 | prevTimer = dwTimer; 121 | 122 | // Are we greater than Ticks Per Frame that would call for 123 | // a frame skip? 124 | if (difference > -TPF) { 125 | calc_run_all(); 126 | while (difference >= TPF) { 127 | calc_run_all(); 128 | difference -= TPF; 129 | } 130 | 131 | int i; 132 | for (i = 0; i < MAX_CALCS; i++) { 133 | if (calcs[i].active) { 134 | frames[i]->gui_draw(); 135 | } 136 | } 137 | // Frame skip if we're too far ahead. 138 | } else { 139 | difference += TPF; 140 | } 141 | } 142 | 143 | void WabbitemuApp::ParseCommandLineArgs() 144 | { 145 | ZeroMemory(&parsedArgs, sizeof(ParsedCmdArgs)); 146 | TCHAR tmpstring[512]; 147 | SEND_FLAG ram = SEND_CUR; 148 | 149 | if (argv && argc > 1) { 150 | _tcscpy(tmpstring, argv[1]); 151 | for(int i = 1; i < argc; i++) { 152 | ZeroMemory(tmpstring, 512); 153 | _tcscpy(tmpstring, argv[i]); 154 | TCHAR secondChar = toupper(tmpstring[1]); 155 | if (*tmpstring != '-' && *tmpstring != '/') { 156 | TCHAR *temp = (TCHAR *) malloc(_tcslen(tmpstring) + 1); 157 | _tcscpy(temp, tmpstring); 158 | temp[_tcslen(tmpstring) + 1] = '\0'; 159 | TCHAR extension[5] = _T(""); 160 | const TCHAR *pext = _tcsrchr(tmpstring, _T('.')); 161 | if (pext != NULL) { 162 | _tcscpy(extension, pext); 163 | } 164 | if (!_tcsicmp(extension, _T(".rom")) || !_tcsicmp(extension, _T(".sav")) || !_tcsicmp(extension, _T(".clc"))) { 165 | parsedArgs.rom_files[parsedArgs.num_rom_files++] = temp; 166 | } 167 | else if (!_tcsicmp(extension, _T(".brk")) || !_tcsicmp(extension, _T(".lab")) 168 | || !_tcsicmp(extension, _T(".zip")) || !_tcsicmp(extension, _T(".tig"))) { 169 | parsedArgs.utility_files[parsedArgs.num_utility_files++] = temp; 170 | } 171 | else if (ram) { 172 | parsedArgs.ram_files[parsedArgs.num_ram_files++] = temp; 173 | } else { 174 | parsedArgs.archive_files[parsedArgs.num_archive_files++] = temp; 175 | } 176 | } else if (secondChar == 'R') { 177 | ram = SEND_RAM; 178 | } else if (secondChar == 'A') { 179 | ram = SEND_ARC; 180 | } else if (secondChar == 'S') { 181 | parsedArgs.silent_mode = TRUE; 182 | } else if (secondChar == 'F') { 183 | parsedArgs.force_focus = TRUE; 184 | } else if (secondChar == 'N') { 185 | parsedArgs.force_new_instance = TRUE; 186 | } 187 | } 188 | } 189 | } 190 | 191 | /*void LoadAlreadyExistingWabbit(unsigned int lParam, LPTSTR filePath, SEND_FLAG sendLoc) 192 | { 193 | HWND hwnd = (HWND) lParam; 194 | COPYDATASTRUCT *cds = (COPYDATASTRUCT *) malloc(sizeof(COPYDATASTRUCT)); 195 | cds->dwData = sendLoc; 196 | size_t strLen; 197 | cds->lpData = filePath; 198 | if (PathIsRelative(filePath)) { 199 | TCHAR tempPath[MAX_PATH]; 200 | TCHAR *tempPath2 = (TCHAR *) malloc(MAX_PATH); 201 | _tgetcwd(tempPath, MAX_PATH); 202 | PathCombine(tempPath2, tempPath, filePath); 203 | cds->lpData = tempPath2; 204 | } 205 | StringCbLength(filePath, 512, &strLen); 206 | cds->cbData = strLen; 207 | SendMessage(hwnd, WM_COPYDATA, (WPARAM) NULL, (LPARAM) cds); 208 | }*/ 209 | 210 | void LoadToLPCALC(INT_PTR lParam, LPTSTR filePath, SEND_FLAG sendLoc) 211 | { 212 | LPCALC lpCalc = (LPCALC) lParam; 213 | SendFile(lpCalc, filePath, sendLoc); 214 | } 215 | 216 | void WabbitemuApp::LoadCommandlineFiles(INT_PTR lParam, void (*load_callback)(INT_PTR, LPTSTR, SEND_FLAG)) 217 | { 218 | //load ROMs first 219 | for (int i = 0; i < parsedArgs.num_rom_files; i++) { 220 | load_callback(lParam, parsedArgs.rom_files[i], SEND_ARC); 221 | } 222 | //then archived files 223 | for (int i = 0; i < parsedArgs.num_archive_files; i++) { 224 | load_callback(lParam, parsedArgs.archive_files[i], SEND_ARC); 225 | } 226 | //then ram 227 | for (int i = 0; i < parsedArgs.num_ram_files; i++) { 228 | load_callback(lParam, parsedArgs.ram_files[i], SEND_RAM); 229 | } 230 | //finally utility files (label, break, etc) 231 | for (int i = 0; i < parsedArgs.num_utility_files; i++) { 232 | load_callback(lParam, parsedArgs.utility_files[i], SEND_ARC); 233 | } 234 | } -------------------------------------------------------------------------------- /gui/guiapp.h: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | #include "gui.h" 3 | #include "calc.h" 4 | #include 5 | 6 | 7 | #define MAX_FILES 255 8 | typedef struct ParsedCmdArgs 9 | { 10 | LPTSTR rom_files[MAX_FILES]; 11 | LPTSTR utility_files[MAX_FILES]; 12 | LPTSTR archive_files[MAX_FILES]; 13 | LPTSTR ram_files[MAX_FILES]; 14 | int num_rom_files; 15 | int num_utility_files; 16 | int num_archive_files; 17 | int num_ram_files; 18 | BOOL silent_mode; 19 | BOOL force_new_instance; 20 | BOOL force_focus; 21 | } ParsedCmdArgs_t; 22 | 23 | 24 | class WabbitemuApp: public wxApp 25 | { 26 | private: 27 | virtual bool OnInit(); 28 | virtual int OnExit(); 29 | void OnTimer(wxTimerEvent& event); 30 | void getTimer(int slot); 31 | void LoadSettings(LPCALC lpCalc); 32 | void SaveSettings(LPCALC lpCalc); 33 | wxConfigBase *settingsConfig; 34 | wxTimer *timer; 35 | unsigned GetTickCount(); 36 | 37 | ParsedCmdArgs_t parsedArgs; 38 | void ParseCommandLineArgs(); 39 | void LoadCommandlineFiles(INT_PTR, void (*load_callback)(INT_PTR, LPTSTR, SEND_FLAG)); 40 | public: 41 | static BOOL DoRomWizard(); 42 | }; 43 | 44 | void LoadToLPCALC(INT_PTR lParam, LPTSTR filePath, SEND_FLAG sendLoc); -------------------------------------------------------------------------------- /gui/guilcd.cpp: -------------------------------------------------------------------------------- 1 | #include "guilcd.h" 2 | #include "gui.h" 3 | #include "core.h" 4 | #include "droptarget.h" 5 | 6 | BEGIN_EVENT_TABLE(WabbitemuLCD, wxWindow) 7 | EVT_PAINT(WabbitemuLCD::OnPaint) 8 | EVT_KEY_DOWN(WabbitemuLCD::OnKeyDown) 9 | EVT_KEY_UP(WabbitemuLCD::OnKeyUp) 10 | 11 | EVT_LEFT_DOWN(WabbitemuLCD::OnLeftButtonDown) 12 | EVT_LEFT_UP(WabbitemuLCD::OnLeftButtonUp) 13 | END_EVENT_TABLE() 14 | 15 | unsigned char redColors[MAX_SHADES+1]; 16 | unsigned char greenColors[MAX_SHADES+1]; 17 | unsigned char blueColors[MAX_SHADES+1]; 18 | WabbitemuLCD::WabbitemuLCD(wxFrame *mainFrame, LPCALC lpCalc) 19 | : wxWindow(mainFrame, ID_LCD, wxPoint(0,0), lpCalc->LCDRect.GetSize()) { 20 | this->lpCalc = lpCalc; 21 | this->mainFrame = mainFrame; 22 | this->SetDropTarget(new DnDFile(this, lpCalc)); 23 | #define LCD_HIGH 255 24 | for (int i = 0; i <= MAX_SHADES; i++) { 25 | redColors[i] = (0x9E*(256-(LCD_HIGH/MAX_SHADES)*i))/255; 26 | greenColors[i] = (0xAB*(256-(LCD_HIGH/MAX_SHADES)*i))/255; 27 | blueColors[i] = (0x88*(256-(LCD_HIGH/MAX_SHADES)*i))/255; 28 | } 29 | hasDrawnLCD = false; 30 | } 31 | 32 | void WabbitemuLCD::OnLeftButtonDown(wxMouseEvent& event) 33 | { 34 | event.Skip(true); 35 | static wxPoint pt; 36 | keypad_t *kp = lpCalc->cpu.pio.keypad; 37 | 38 | //CopySkinToButtons(); 39 | //CaptureMouse(); 40 | pt.x = event.GetX(); 41 | pt.y = event.GetY(); 42 | /*if (lpCalc->bCutout) { 43 | pt.y += GetSystemMetrics(SM_CYCAPTION); 44 | pt.x += GetSystemMetrics(SM_CXSIZEFRAME); 45 | }*/ 46 | for(int group = 0; group < 7; group++) { 47 | for(int bit = 0; bit < 8; bit++) { 48 | kp->keys[group][bit] &= (~KEY_MOUSEPRESS); 49 | } 50 | } 51 | 52 | lpCalc->cpu.pio.keypad->on_pressed &= ~KEY_MOUSEPRESS; 53 | 54 | /*if (!event.LeftDown()) { 55 | //FinalizeButtons(lpCalc); 56 | return; 57 | }*/ 58 | 59 | if (lpCalc->keymap.GetRed(pt.x, pt.y) == 0xFF) { 60 | //FinalizeButtons(lpCalc); 61 | return; 62 | } 63 | 64 | int green = lpCalc->keymap.GetGreen(pt.x, pt.y); 65 | int blue = lpCalc->keymap.GetBlue(pt.x, pt.y); 66 | if ((green >> 4) == 0x05 && (blue >> 4) == 0x00) 67 | { 68 | lpCalc->cpu.pio.keypad->on_pressed |= KEY_MOUSEPRESS; 69 | } else { 70 | kp->keys[green >> 4][blue >> 4] |= KEY_MOUSEPRESS; 71 | if ((kp->keys[green >> 4][blue >> 4] & KEY_STATEDOWN) == 0) { 72 | //DrawButtonState(lpCalc, lpCalc->hdcButtons, lpCalc->hdcKeymap, &pt, DBS_DOWN | DBS_PRESS); 73 | kp->keys[green >> 4][blue >> 4] |= KEY_STATEDOWN; 74 | } 75 | } 76 | } 77 | 78 | void WabbitemuLCD::OnLeftButtonUp(wxMouseEvent& event) 79 | { 80 | event.Skip(true); 81 | static wxPoint pt; 82 | keypad_t *kp = lpCalc->cpu.pio.keypad; 83 | 84 | //ReleaseMouse(); 85 | 86 | for(int group = 0; group < 7; group++) { 87 | for(int bit = 0; bit < 8; bit++) { 88 | kp->keys[group][bit] &= ~(KEY_MOUSEPRESS | KEY_STATEDOWN); 89 | } 90 | } 91 | 92 | lpCalc->cpu.pio.keypad->on_pressed &= ~KEY_MOUSEPRESS; 93 | } 94 | 95 | void WabbitemuLCD::OnResize(wxSizeEvent& event) 96 | { 97 | event.Skip(false); 98 | } 99 | 100 | //TODO: forward these events somehow 101 | void WabbitemuLCD::OnKeyDown(wxKeyEvent& event) 102 | { 103 | int keycode = event.GetKeyCode(); 104 | if (keycode == WXK_F8) { 105 | if (lpCalc->speed == 100) 106 | lpCalc->speed = 400; 107 | else 108 | lpCalc->speed = 100; 109 | } 110 | if (keycode == WXK_SHIFT) { 111 | wxUint32 raw = event.GetRawKeyCode(); 112 | if (raw == 65505) { 113 | keycode = WXK_LSHIFT; 114 | } else { 115 | keycode = WXK_RSHIFT; 116 | } 117 | } 118 | 119 | keyprog_t *kp = keypad_key_press(&lpCalc->cpu, keycode); 120 | if (kp) { 121 | if ((lpCalc->cpu.pio.keypad->keys[kp->group][kp->bit] & KEY_STATEDOWN) == 0) { 122 | lpCalc->cpu.pio.keypad->keys[kp->group][kp->bit] |= KEY_STATEDOWN; 123 | this->Update(); 124 | FinalizeButtons(); 125 | } 126 | } 127 | } 128 | 129 | void WabbitemuLCD::OnKeyUp(wxKeyEvent& event) 130 | { 131 | int key = event.GetKeyCode(); 132 | if (key == WXK_SHIFT) { 133 | keypad_key_release(&lpCalc->cpu, WXK_LSHIFT); 134 | keypad_key_release(&lpCalc->cpu, WXK_RSHIFT); 135 | } else { 136 | keypad_key_release(&lpCalc->cpu, key); 137 | } 138 | FinalizeButtons(); 139 | } 140 | 141 | void WabbitemuLCD::FinalizeButtons() { 142 | int group, bit; 143 | keypad_t *kp = lpCalc->cpu.pio.keypad; 144 | for(group = 0; group < 7; group++) { 145 | for(bit = 0; bit < 8; bit++) { 146 | if ((kp->keys[group][bit] & KEY_STATEDOWN) && 147 | ((kp->keys[group][bit] & KEY_MOUSEPRESS) == 0) && 148 | ((kp->keys[group][bit] & KEY_KEYBOARDPRESS) == 0)) { 149 | kp->keys[group][bit] &= (~KEY_STATEDOWN); 150 | } 151 | } 152 | } 153 | } 154 | 155 | void WabbitemuLCD::OnPaint(wxPaintEvent& event) 156 | { 157 | if (this->mainFrame->IsIconized()) { 158 | return; 159 | } 160 | wxPaintDC dc(this); 161 | PaintLCD(this, &dc); 162 | LCD_t *lcd = lpCalc->cpu.pio.lcd; 163 | wxStatusBar *wxStatus = mainFrame->GetStatusBar(); 164 | if (wxStatus) { 165 | if (clock() > lpCalc->sb_refresh + CLOCKS_PER_SEC / 2) { 166 | wxString sz_status; 167 | if (lcd->active) { 168 | sz_status.sprintf(wxT("FPS: %0.2lf"), lcd->ufps); 169 | } else { 170 | sz_status.sprintf(wxT("FPS: -")); 171 | } 172 | wxStatus->SetStatusText(sz_status, 0); 173 | lpCalc->sb_refresh = clock(); 174 | } 175 | } 176 | } 177 | 178 | void WabbitemuLCD::PaintLCD(wxWindow *window, wxPaintDC *wxDCDest) 179 | { 180 | unsigned char *screen; 181 | LCD_t *lcd = lpCalc->cpu.pio.lcd; 182 | wxSize rc = lpCalc->LCDRect.GetSize(); 183 | int scale = lpCalc->scale; 184 | int draw_width = lpCalc->LCDRect.GetWidth(); 185 | int draw_height = lpCalc->LCDRect.GetHeight(); 186 | wxPoint drawPoint(0, 0); 187 | wxMemoryDC wxMemDC; 188 | if (lcd->active == false) { 189 | unsigned char lcd_data[128*64]; 190 | memset(lcd_data, 0, sizeof(lcd_data)); 191 | unsigned char rgb_data[128*64*3]; 192 | int i, j; 193 | for (i = j = 0; i < 128*64; i++, j+=3) { 194 | rgb_data[j] = redColors[lcd_data[i]]; 195 | rgb_data[j+1] = greenColors[lcd_data[i]]; 196 | rgb_data[j+2] = blueColors[lcd_data[i]]; 197 | } 198 | wxImage screenImage(128, 64, rgb_data, true); 199 | wxBitmap bmpBuf(screenImage.Size(wxSize(lcd->width, 64), wxPoint(0, 0)).Scale(rc.GetWidth(), rc.GetHeight())); 200 | wxMemDC.SelectObject(bmpBuf); 201 | //draw drag panes 202 | /*if (lpCalc->do_drag == TRUE) { 203 | 204 | hdcOverlay = DrawDragPanes(hwnd, hdcDest, 0); 205 | BLENDFUNCTION bf; 206 | bf.BlendOp = AC_SRC_OVER; 207 | bf.BlendFlags = 0; 208 | bf.SourceConstantAlpha = 160; 209 | bf.AlphaFormat = 0; 210 | if (AlphaBlend( hdc, 0, 0, rc.right, rc.bottom, 211 | hdcOverlay, 0, 0, rc.right, rc.bottom, 212 | bf ) == FALSE) printf("alpha blend 1 failed\n"); 213 | 214 | DeleteDC(hdcOverlay); 215 | 216 | }*/ 217 | 218 | //copy to the screen 219 | wxDCDest->Blit(drawPoint.x, drawPoint.y, draw_width, draw_height, &wxMemDC, 0, 0); 220 | wxMemDC.SelectObject(wxNullBitmap); 221 | 222 | } else { 223 | screen = LCD_image( lpCalc->cpu.pio.lcd ) ; 224 | unsigned char rgb_data[128*64*3]; 225 | int i, j; 226 | for (i = j = 0; i < 128*64; i++, j+=3) { 227 | rgb_data[j] = redColors[screen[i]]; 228 | rgb_data[j+1] = greenColors[screen[i]]; 229 | rgb_data[j+2] = blueColors[screen[i]]; 230 | } 231 | 232 | /*wxImageResizeQuality scalingMode = wxIMAGE_QUALITY_NORMAL; 233 | //hiqh quality does bicubic sampling which looks terrible on our image 234 | if (lcd->width * lpCalc->scale != rc.GetWidth()) 235 | scalingMode = wxIMAGE_QUALITY_HIGH; 236 | else 237 | scalingMode = wxIMAGE_QUALITY_NORMAL;*/ 238 | wxImage screenImage(128, 64, rgb_data, true); 239 | wxBitmap bmpBuf(screenImage.Size(wxSize(lcd->width, 64), wxPoint(0, 0)).Scale(rc.GetWidth(), rc.GetHeight())); 240 | wxMemDC.SelectObject(bmpBuf); 241 | //if were dragging something we will draw these nice panes 242 | /*BLENDFUNCTION bf; 243 | bf.BlendOp = AC_SRC_OVER; 244 | bf.BlendFlags = 0; 245 | bf.SourceConstantAlpha = 160; 246 | bf.AlphaFormat = 0; 247 | 248 | if (lpCalc->do_drag == TRUE) { 249 | 250 | hdcOverlay = DrawDragPanes(hwnd, hdcDest, 0); 251 | 252 | if (AlphaBlend( hdc, 0, 0, rc.right, rc.bottom, 253 | hdcOverlay, 0, 0, rc.right, rc.bottom, 254 | bf ) == FALSE) printf("alpha blend 1 failed\n"); 255 | 256 | DeleteDC(hdcOverlay); 257 | 258 | }*/ 259 | //finally copy up the screen image 260 | wxDCDest->Blit(drawPoint.x, drawPoint.y, draw_width, draw_height, &wxMemDC, 0, 0); 261 | //lets give it a texture to look nice 262 | wxImage skinTexture = lpCalc->calcSkin.GetSubImage(lpCalc->LCDRect); 263 | int textureSize = lpCalc->LCDRect.GetWidth() * lpCalc->LCDRect.GetHeight(); 264 | unsigned char *alpha = (unsigned char *) malloc(textureSize); 265 | memset(alpha, 108, textureSize); 266 | skinTexture.SetAlpha(alpha); 267 | wxDCDest->DrawBitmap(skinTexture, drawPoint.x, drawPoint.y, true); 268 | wxMemDC.SelectObject(wxNullBitmap); 269 | 270 | } 271 | } -------------------------------------------------------------------------------- /gui/guilcd.h: -------------------------------------------------------------------------------- 1 | #ifndef GUILCD_WX_H 2 | #define GUILCD_WX_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include "calc.h" 9 | #include "lcd.h" 10 | #include 11 | 12 | void SaveStateDialog(LPCALC lpCalc); 13 | #define MAX_SHADES 255 14 | class WabbitemuLCD: public wxWindow 15 | { 16 | public: 17 | WabbitemuLCD(wxFrame *mainFrame, LPCALC lpCalc); 18 | 19 | void PaintNow(); 20 | protected: 21 | DECLARE_EVENT_TABLE() 22 | private: 23 | void OnKeyDown(wxKeyEvent& event); 24 | void OnKeyUp(wxKeyEvent& event); 25 | void PaintLCD(wxWindow *, wxPaintDC *); 26 | void OnPaint(wxPaintEvent& event); 27 | void OnResize(wxSizeEvent& event); 28 | void OnLeftButtonDown(wxMouseEvent& event); 29 | void OnLeftButtonUp(wxMouseEvent& event); 30 | void FinalizeButtons(); 31 | 32 | bool hasDrawnLCD; 33 | LPCALC lpCalc; 34 | wxFrame *mainFrame; 35 | }; 36 | 37 | #endif 38 | -------------------------------------------------------------------------------- /gui/guiopenfile.cpp: -------------------------------------------------------------------------------- 1 | #include "guiopenfile.h" 2 | #include "calc.h" 3 | #include "SendFile.h" 4 | 5 | -------------------------------------------------------------------------------- /gui/guiopenfile.h: -------------------------------------------------------------------------------- 1 | #ifndef GUIOPENFILE_H 2 | #define GUIOPENFILE_H 3 | #include "gui.h" 4 | 5 | void GetOpenSendFileName(LPCALC, int defFilter); 6 | #endif 7 | -------------------------------------------------------------------------------- /gui/guisavestate.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/guisavestate.c -------------------------------------------------------------------------------- /gui/guisavestate.cpp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/guisavestate.cpp -------------------------------------------------------------------------------- /gui/guiskinwindow.cpp: -------------------------------------------------------------------------------- 1 | #include "guiskinwindow.h" 2 | #include "droptarget.h" 3 | 4 | BEGIN_EVENT_TABLE(SkinWindow, wxWindow) 5 | EVT_PAINT(SkinWindow::OnPaint) 6 | EVT_LEFT_DOWN(SkinWindow::OnLeftButtonDown) 7 | EVT_LEFT_UP(SkinWindow::OnLeftButtonUp) 8 | EVT_KEY_DOWN(SkinWindow::OnKeyDown) 9 | EVT_KEY_UP(SkinWindow::OnKeyUp) 10 | END_EVENT_TABLE() 11 | 12 | SkinWindow::SkinWindow(wxFrame *parent, LPCALC lpCalc) : wxWindow(parent, wxID_ANY) 13 | { 14 | this->lpCalc = lpCalc; 15 | this->SetDropTarget(new DnDFile(this, lpCalc)); 16 | } 17 | 18 | void SkinWindow::OnPaint(wxPaintEvent &event) { 19 | wxPaintDC dc(this); 20 | if (lpCalc->SkinEnabled) { 21 | dc.DrawBitmap(lpCalc->calcSkin, 0, 0, true); 22 | } 23 | } 24 | 25 | void SkinWindow::OnLeftButtonDown(wxMouseEvent& event) 26 | { 27 | event.Skip(true); 28 | static wxPoint pt; 29 | keypad_t *kp = lpCalc->cpu.pio.keypad; 30 | 31 | //CopySkinToButtons(); 32 | //CaptureMouse(); 33 | pt.x = event.GetX(); 34 | pt.y = event.GetY(); 35 | /*if (lpCalc->bCutout) { 36 | pt.y += GetSystemMetrics(SM_CYCAPTION); 37 | pt.x += GetSystemMetrics(SM_CXSIZEFRAME); 38 | }*/ 39 | for(int group = 0; group < 7; group++) { 40 | for(int bit = 0; bit < 8; bit++) { 41 | kp->keys[group][bit] &= (~KEY_MOUSEPRESS); 42 | } 43 | } 44 | 45 | lpCalc->cpu.pio.keypad->on_pressed &= ~KEY_MOUSEPRESS; 46 | 47 | /*if (!event.LeftDown()) { 48 | //FinalizeButtons(lpCalc); 49 | return; 50 | }*/ 51 | 52 | if (lpCalc->keymap.GetRed(pt.x, pt.y) == 0xFF) { 53 | //FinalizeButtons(lpCalc); 54 | return; 55 | } 56 | 57 | int green = lpCalc->keymap.GetGreen(pt.x, pt.y); 58 | int blue = lpCalc->keymap.GetBlue(pt.x, pt.y); 59 | if ((green >> 4) == 0x05 && (blue >> 4) == 0x00) 60 | { 61 | lpCalc->cpu.pio.keypad->on_pressed |= KEY_MOUSEPRESS; 62 | } else { 63 | kp->keys[green >> 4][blue >> 4] |= KEY_MOUSEPRESS; 64 | if ((kp->keys[green >> 4][blue >> 4] & KEY_STATEDOWN) == 0) { 65 | //DrawButtonState(lpCalc, lpCalc->hdcButtons, lpCalc->hdcKeymap, &pt, DBS_DOWN | DBS_PRESS); 66 | kp->keys[green >> 4][blue >> 4] |= KEY_STATEDOWN; 67 | } 68 | } 69 | } 70 | 71 | void SkinWindow::OnLeftButtonUp(wxMouseEvent& event) 72 | { 73 | event.Skip(true); 74 | static wxPoint pt; 75 | keypad_t *kp = lpCalc->cpu.pio.keypad; 76 | 77 | //ReleaseMouse(); 78 | 79 | for(int group = 0; group < 7; group++) { 80 | for(int bit = 0; bit < 8; bit++) { 81 | kp->keys[group][bit] &= ~(KEY_MOUSEPRESS | KEY_STATEDOWN); 82 | } 83 | } 84 | 85 | lpCalc->cpu.pio.keypad->on_pressed &= ~KEY_MOUSEPRESS; 86 | } 87 | 88 | void SkinWindow::OnKeyDown(wxKeyEvent& event) 89 | { 90 | int keycode = event.GetKeyCode(); 91 | if (keycode == WXK_SHIFT) { 92 | wxUint32 raw = event.GetRawKeyCode(); 93 | if (raw == 65505) { 94 | keycode = WXK_LSHIFT; 95 | } else { 96 | keycode = WXK_RSHIFT; 97 | } 98 | } 99 | 100 | keyprog_t *kp = keypad_key_press(&lpCalc->cpu, keycode); 101 | if (kp) { 102 | if ((lpCalc->cpu.pio.keypad->keys[kp->group][kp->bit] & KEY_STATEDOWN) == 0) { 103 | lpCalc->cpu.pio.keypad->keys[kp->group][kp->bit] |= KEY_STATEDOWN; 104 | this->Update(); 105 | FinalizeButtons(); 106 | } 107 | } 108 | } 109 | 110 | void SkinWindow::OnKeyUp(wxKeyEvent& event) 111 | { 112 | int key = event.GetKeyCode(); 113 | if (key == WXK_SHIFT) { 114 | keypad_key_release(&lpCalc->cpu, WXK_LSHIFT); 115 | keypad_key_release(&lpCalc->cpu, WXK_RSHIFT); 116 | } else { 117 | keypad_key_release(&lpCalc->cpu, key); 118 | } 119 | FinalizeButtons(); 120 | } 121 | 122 | void SkinWindow::FinalizeButtons() { 123 | int group, bit; 124 | keypad_t *kp = lpCalc->cpu.pio.keypad; 125 | for(group = 0; group < 7; group++) { 126 | for(bit = 0; bit < 8; bit++) { 127 | if ((kp->keys[group][bit] & KEY_STATEDOWN) && 128 | ((kp->keys[group][bit] & KEY_MOUSEPRESS) == 0) && 129 | ((kp->keys[group][bit] & KEY_KEYBOARDPRESS) == 0)) { 130 | kp->keys[group][bit] &= (~KEY_STATEDOWN); 131 | } 132 | } 133 | } 134 | } -------------------------------------------------------------------------------- /gui/guiskinwindow.h: -------------------------------------------------------------------------------- 1 | #ifndef GUISKINWINDOW_H 2 | #define GUISKINWINDOW_H 3 | 4 | #include 5 | #include "calc.h" 6 | 7 | class SkinWindow : public wxWindow 8 | { 9 | private: 10 | LPCALC lpCalc; 11 | void OnPaint(wxPaintEvent &event); 12 | void OnLeftButtonDown(wxMouseEvent& event); 13 | void OnLeftButtonUp(wxMouseEvent& event); 14 | void OnKeyDown(wxKeyEvent& event); 15 | void OnKeyUp(wxKeyEvent& event); 16 | void FinalizeButtons(); 17 | protected: 18 | DECLARE_EVENT_TABLE() 19 | public: 20 | SkinWindow(wxFrame *parent, LPCALC lpCalc); 21 | }; 22 | 23 | #endif -------------------------------------------------------------------------------- /gui/guivartree.h: -------------------------------------------------------------------------------- 1 | #ifndef GUIVARTREE_H 2 | #define GUIVARTREE_H 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | #include "calc.h" 9 | #include "link.h" 10 | 11 | typedef struct{ 12 | int model; 13 | wxTreeItemId hRoot; 14 | union { 15 | struct { 16 | wxTreeItemId *hAppVar; 17 | wxTreeItemId *hEquation; 18 | wxTreeItemId *hGDB; 19 | wxTreeItemId *hList; 20 | wxTreeItemId *hMatrix; 21 | wxTreeItemId *hNumber; 22 | wxTreeItemId *hPic; 23 | wxTreeItemId *hProgram; 24 | wxTreeItemId *hString; 25 | wxTreeItemId *hGroup; 26 | wxTreeItemId *hApplication; 27 | }; 28 | wxTreeItemId *hTypes[11]; 29 | }; 30 | int count; 31 | wxTreeItemId *hApps[96]; 32 | applist_t applist; 33 | wxTreeItemId *hVars[512]; 34 | symlist_t sym; 35 | } VARTREEVIEW_t; 36 | 37 | enum { 38 | TI_ICON_BLANK, 39 | TI_ICON_84PSE, 40 | TI_ICON_ARCHIVE, 41 | TI_ICON_APPVAR, 42 | TI_ICON_DEVICE_SETTINGS, 43 | TI_ICON_EQUATIONS, 44 | TI_ICON_GDB, 45 | TI_ICON_LIST, 46 | TI_ICON_MATRIX, 47 | TI_ICON_NUMBER, 48 | TI_ICON_PROGRAM, 49 | TI_ICON_STRING, 50 | TI_ICON_PIC, 51 | TI_ICON_APP, 52 | TI_ICON_GROUP, 53 | TI_ICON_UKNOWN, 54 | TI_ICON_FILE, 55 | TI_ICON_FILE_RAM, 56 | TI_ICON_FILE_ARC 57 | }; 58 | 59 | class VarTree : public wxFrame { 60 | private: 61 | wxButton* m_refreshButton; 62 | wxButton* m_exportButton; 63 | wxTreeCtrl* m_treeVariables; 64 | wxStaticText* m_staticAddressText; 65 | wxStaticText* m_staticRamText; 66 | wxStaticText* m_staticPageText; 67 | wxStaticText* m_staticNameText; 68 | wxImageList* imageList; 69 | wxBoxSizer* bSizer53; 70 | wxBoxSizer* bSizer54; 71 | wxGridSizer* gSizer9; 72 | 73 | apphdr_t *GetAppVariable(wxTreeItemId &hTreeItem, int &slot); 74 | symbol83P_t *GetSymbolVariable(wxTreeItemId &hTreeItem, int &slot); 75 | int FillDesc(wxTreeItemId &hSelect, TCHAR *filePath); 76 | void *FillFileBuffer(wxTreeItemId &hSelect, void *buf); 77 | int SetVarName(TCHAR *filePath); 78 | void OnTreeSelChanged(wxTreeEvent &event); 79 | void OnRefresh(wxCommandEvent &event); 80 | void OnExport(wxCommandEvent &event); 81 | 82 | VARTREEVIEW_t Tree[MAX_CALCS]; 83 | TCHAR export_file_name[512]; 84 | bool Tree_init; 85 | protected: 86 | DECLARE_EVENT_TABLE() 87 | public: 88 | VarTree(wxWindow *window); 89 | ~VarTree(); 90 | void UpdateVarTree(bool New); 91 | }; 92 | 93 | #endif -------------------------------------------------------------------------------- /gui/rom/Rom82.82p: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/rom/Rom82.82p -------------------------------------------------------------------------------- /gui/rom/Rom83.83p: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/rom/Rom83.83p -------------------------------------------------------------------------------- /gui/rom/Rom85.85s: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/rom/Rom85.85s -------------------------------------------------------------------------------- /gui/rom/Rom86.86p: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/rom/Rom86.86p -------------------------------------------------------------------------------- /gui/rom/rom8x.8xp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/rom/rom8x.8xp -------------------------------------------------------------------------------- /gui/skins/TI-73.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-73.png -------------------------------------------------------------------------------- /gui/skins/TI-82.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-82.png -------------------------------------------------------------------------------- /gui/skins/TI-83+.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-83+.png -------------------------------------------------------------------------------- /gui/skins/TI-83+Keymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-83+Keymap.png -------------------------------------------------------------------------------- /gui/skins/TI-83+SE.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-83+SE.png -------------------------------------------------------------------------------- /gui/skins/TI-83.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-83.png -------------------------------------------------------------------------------- /gui/skins/TI-83Keymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/TI-83Keymap.png -------------------------------------------------------------------------------- /gui/skins/ti-81.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-81.png -------------------------------------------------------------------------------- /gui/skins/ti-81keymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-81keymap.png -------------------------------------------------------------------------------- /gui/skins/ti-82keymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-82keymap.png -------------------------------------------------------------------------------- /gui/skins/ti-84+.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-84+.png -------------------------------------------------------------------------------- /gui/skins/ti-84+se.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-84+se.png -------------------------------------------------------------------------------- /gui/skins/ti-84+sekeymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-84+sekeymap.png -------------------------------------------------------------------------------- /gui/skins/ti-85.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-85.png -------------------------------------------------------------------------------- /gui/skins/ti-85Keymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-85Keymap.png -------------------------------------------------------------------------------- /gui/skins/ti-86.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-86.png -------------------------------------------------------------------------------- /gui/skins/ti-86keymap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/skins/ti-86keymap.png -------------------------------------------------------------------------------- /gui/wabbiticon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/gui/wabbiticon.png -------------------------------------------------------------------------------- /gui/wabbiticon.xpm: -------------------------------------------------------------------------------- 1 | /* XPM */ 2 | static const char * wabbiticon_xpm[] = { 3 | "16 16 5 1", 4 | " c None", 5 | ". c #181818", 6 | "+ c #D6D6D6", 7 | "@ c #FFFFFF", 8 | "# c #737373", 9 | " ", 10 | " .. ", 11 | " .+@. ", 12 | " .#@. ", 13 | " ....#@. ", 14 | " .+@@+.#@. ", 15 | " .+@@@@@@@+. ", 16 | " ..+@@@@@@@@@+. ", 17 | ".@@@@@@@@@@@.@+.", 18 | ".@+@@@@@@@@@.@+.", 19 | " .+@@@@+@@@@++#.", 20 | " .+@@+..+@@@+. ", 21 | " .+@@@+.@+.. ", 22 | " ......... ", 23 | " ", 24 | " "}; 25 | -------------------------------------------------------------------------------- /gui/wizard/romwizard.cpp: -------------------------------------------------------------------------------- 1 | #include "romwizard.h" 2 | #include "gui.h" 3 | #include "fileutilities.h" 4 | #include "exportvar.h" 5 | 6 | #include "rom/bf73.h" 7 | #include "rom/bf83p.h" 8 | #include "rom/bf83pse.h" 9 | #include "rom/bf84p.h" 10 | #include "rom/bf84pse.h" 11 | 12 | BEGIN_EVENT_TABLE(RomWizard, wxWizard) 13 | EVT_WIZARD_FINISHED(wxID_ANY, RomWizard::OnFinish) 14 | EVT_WIZARD_PAGE_CHANGED(wxID_ANY, RomWizard::OnPageChanged) 15 | EVT_WIZARD_PAGE_CHANGING(wxID_ANY, RomWizard::OnPageChanging) 16 | END_EVENT_TABLE() 17 | 18 | RomWizard::RomWizard() : wxWizard (NULL, wxID_ANY, _T("ROM Wizard")) { 19 | startPage = new WizardStartPage(this); 20 | calcTypePage = new WizardCalcTypePage(this); 21 | startPage->next = calcTypePage; 22 | calcTypePage->prev = startPage; 23 | osPage = new WizardOSPage(this); 24 | calcTypePage->next = osPage; 25 | osPage->prev = calcTypePage; 26 | SetPageSize(startPage->GetBestSize()); 27 | 28 | // Set defaults for the start page 29 | wxWindow *win = FindWindowById(wxID_FORWARD, this); 30 | win->SetLabel(wxT("Finish")); 31 | win->Enable(false); 32 | } 33 | 34 | bool RomWizard::Begin() { 35 | return this->RunWizard(startPage); 36 | } 37 | 38 | // Dirty hack to prevent buggy wx versions from moving forward 39 | // or backwards when the button itself is disabled 40 | void RomWizard::OnPageChanging(wxWizardEvent &event) { 41 | wxWindow *win; 42 | if (event.GetDirection()) { 43 | // Going forward 44 | win = FindWindowById(wxID_FORWARD, this); 45 | } else { 46 | // Going backward 47 | win = FindWindowById(wxID_BACKWARD, this); 48 | } 49 | 50 | // If the button isn't enabled, veto the event! 51 | if (!win->IsEnabled()) { 52 | event.Veto(); 53 | } 54 | } 55 | 56 | void RomWizard::OnPageChanged(wxWizardEvent &event) { 57 | if (calcTypePage == event.GetPage()) { 58 | wxWindow *win = FindWindowById(wxID_FORWARD, this); 59 | if (startPage->m_copyRadio->GetValue()) { 60 | calcTypePage->EnableRadios(true); 61 | } else { 62 | calcTypePage->EnableRadios(false); 63 | } 64 | win->Enable(true); 65 | } else if (osPage == event.GetPage()) { 66 | osPage->creatingROM = startPage->m_createRadio->GetValue(); 67 | wxWindow *win = FindWindowById(wxID_FORWARD, this); 68 | if (osPage->creatingROM) { 69 | win->SetLabel(_T("Finish")); 70 | } else { 71 | win->SetLabel(_T("Next >")); 72 | } 73 | osPage->UpdateOSPathState(); 74 | } 75 | } 76 | 77 | void RomWizard::ModelInit(LPCALC lpCalc, int model) 78 | { 79 | switch(model) { 80 | case TI_73: 81 | calc_init_83p(lpCalc); 82 | break; 83 | case TI_83P: 84 | calc_init_83p(lpCalc); 85 | break; 86 | case TI_83PSE: 87 | calc_init_83pse(lpCalc); 88 | break; 89 | case TI_84P: 90 | calc_init_84p(lpCalc); 91 | break; 92 | case TI_84PSE: 93 | calc_init_83pse(lpCalc); 94 | break; 95 | } 96 | } 97 | 98 | BOOL RomWizard::ExtractBootFree(wxString &bootfreePath, int model) { 99 | wxString tempFile = wxFileName::GetTempDir(); 100 | tempFile.Append(_T("/bootfree.hex")); 101 | bootfreePath = tempFile; 102 | FILE *file = fopen(tempFile.mb_str(), "wb"); 103 | const unsigned char *output; 104 | size_t size; 105 | switch(model) { 106 | case TI_73: 107 | output = bf73_hex; 108 | size = sizeof(bf73_hex); 109 | break; 110 | case TI_83P: 111 | output = bf83pbe_hex; 112 | size = sizeof(bf83pbe_hex); 113 | break; 114 | case TI_83PSE: 115 | output = bf83pse_hex; 116 | size = sizeof(bf83pse_hex); 117 | break; 118 | case TI_84P: 119 | output = bf84pbe_hex; 120 | size = sizeof(bf84pbe_hex); 121 | break; 122 | case TI_84PSE: 123 | output = bf84pse_hex; 124 | size = sizeof(bf84pse_hex); 125 | break; 126 | } 127 | for (int i = 0; i < size; i++) { 128 | fputc(output[i], file); 129 | } 130 | fclose(file); 131 | return TRUE; 132 | } 133 | 134 | void RomWizard::OnFinish(wxWizardEvent &event) { 135 | if (startPage->m_browseRadio->GetValue()) { 136 | wxString path = startPage->m_filePicker1->GetPath(); 137 | LPCALC lpCalc = calc_slot_new(); 138 | BOOL success = rom_load(lpCalc, path.c_str()); 139 | if (!success) { 140 | //should never get here 141 | return; 142 | } 143 | gui_frame(lpCalc); 144 | return; 145 | } 146 | if (startPage->m_createRadio->GetValue()) { 147 | TCHAR buffer[255]; 148 | wxString osPath; 149 | int model = calcTypePage->GetModel(); 150 | 151 | if (!SaveFile(buffer, _T("ROMs (*.rom)\0*.rom\0Bins (*.bin)\0*.bin\0All Files (*.*)\0*.*\0\0"), 152 | _T("Wabbitemu Export Rom"), _T("rom"))) { 153 | printf("Going for save! [%254s]\n", buffer); 154 | osPath = osPage->m_filePicker2->GetPath(); 155 | 156 | //if you don't want to load an OS, fine... 157 | if (osPath.length() > 0) { 158 | TIFILE_t *tifile = newimportvar(osPath); 159 | if (tifile == NULL || tifile->type != FLASH_TYPE) { 160 | wxMessageBox(_T("Error: OS file is corrupt!"), _T("Error"), wxOK | wxICON_ERROR); 161 | return; 162 | } else { 163 | LPCALC lpCalc = calc_slot_new(); 164 | //ok yes i know this is retarded...but this way we can use Load_8xu 165 | //outside this function... 166 | wxString hexFile; 167 | ExtractBootFree(hexFile, model); 168 | ModelInit(lpCalc, model); 169 | //slot stuff 170 | //LoadRegistrySettings(lpCalc); 171 | _tcscpy(lpCalc->rom_path, osPath.c_str()); 172 | 173 | lpCalc->active = TRUE; 174 | lpCalc->model = model; 175 | lpCalc->cpu.pio.model = model; 176 | FILE *file = fopen(hexFile.fn_str(), "rb"); 177 | writeboot(file, &lpCalc->mem_c, -1); 178 | fclose(file); 179 | remove(hexFile.fn_str()); 180 | 181 | calc_erase_certificate(lpCalc->mem_c.flash,lpCalc->mem_c.flash_size); 182 | calc_reset(lpCalc); 183 | //calc_turn_on(lpCalc); 184 | gui_frame(lpCalc); 185 | //write the output from file 186 | MFILE *romfile = ExportRom(buffer, lpCalc); 187 | mclose(romfile); 188 | 189 | forceload_os(&lpCalc->cpu, tifile); 190 | } 191 | } 192 | } 193 | } 194 | } 195 | -------------------------------------------------------------------------------- /gui/wizard/romwizard.h: -------------------------------------------------------------------------------- 1 | #ifndef ROMWIZARD_H 2 | #define ROMWIZARD_H 3 | #include "wizard/wizardstart.h" 4 | #include "wizard/wizardcalctype.h" 5 | #include "wizard/wizardos.h" 6 | #include 7 | #include 8 | #include 9 | 10 | class RomWizard : public wxWizard { 11 | private: 12 | WizardStartPage *startPage; 13 | WizardCalcTypePage *calcTypePage; 14 | WizardOSPage *osPage; 15 | void OnFinish(wxWizardEvent &); 16 | void OnPageChanged(wxWizardEvent &); 17 | void OnPageChanging(wxWizardEvent &); 18 | void ModelInit(LPCALC lpCalc, int model); 19 | BOOL ExtractBootFree(wxString &bootfreePath, int model); 20 | protected: 21 | DECLARE_EVENT_TABLE() 22 | public: 23 | RomWizard(); 24 | bool Begin(); 25 | }; 26 | 27 | #endif 28 | -------------------------------------------------------------------------------- /gui/wizard/wizardcalctype.cpp: -------------------------------------------------------------------------------- 1 | #include "wizardcalctype.h" 2 | 3 | WizardCalcTypePage::WizardCalcTypePage( wxWizard* parent ) : wxWizardPage(parent) 4 | { 5 | wxBoxSizer* bSizer19; 6 | bSizer19 = new wxBoxSizer( wxVERTICAL ); 7 | 8 | m_staticText2 = new wxStaticText( this, wxID_ANY, wxT("What type of calculator would you like to emulate?"), wxDefaultPosition, wxDefaultSize, 0 ); 9 | m_staticText2->Wrap( -1 ); 10 | bSizer19->Add( m_staticText2, 0, wxALL, 5 ); 11 | 12 | wxGridSizer* gSizer6; 13 | gSizer6 = new wxGridSizer( 3, 3, 0, 0 ); 14 | 15 | m_calc73 = new wxRadioButton( this, wxID_ANY, wxT("TI-73"), wxDefaultPosition, wxDefaultSize, wxRB_GROUP ); 16 | gSizer6->Add( m_calc73, 0, wxALL, 5 ); 17 | 18 | m_calc82 = new wxRadioButton( this, wxID_ANY, wxT("TI-82"), wxDefaultPosition, wxDefaultSize, 0 ); 19 | gSizer6->Add( m_calc82, 0, wxALL, 5 ); 20 | 21 | m_calc83 = new wxRadioButton( this, wxID_ANY, wxT("TI-83"), wxDefaultPosition, wxDefaultSize, 0 ); 22 | gSizer6->Add( m_calc83, 0, wxALL, 5 ); 23 | 24 | m_calc83p = new wxRadioButton( this, wxID_ANY, wxT("TI-83 Plus"), wxDefaultPosition, wxDefaultSize, 0 ); 25 | gSizer6->Add( m_calc83p, 0, wxALL, 5 ); 26 | 27 | m_calc83pse = new wxRadioButton( this, wxID_ANY, wxT("TI-83 Plus SE"), wxDefaultPosition, wxDefaultSize, 0 ); 28 | gSizer6->Add( m_calc83pse, 0, wxALL, 5 ); 29 | 30 | m_calc84p = new wxRadioButton( this, wxID_ANY, wxT("TI-84 Plus"), wxDefaultPosition, wxDefaultSize, 0 ); 31 | gSizer6->Add( m_calc84p, 0, wxALL, 5 ); 32 | 33 | m_calc84pse = new wxRadioButton( this, wxID_ANY, wxT("TI-84 Plus SE"), wxDefaultPosition, wxDefaultSize, 0 ); 34 | gSizer6->Add( m_calc84pse, 0, wxALL, 5 ); 35 | 36 | m_calc85 = new wxRadioButton( this, wxID_ANY, wxT("TI-85"), wxDefaultPosition, wxDefaultSize, 0 ); 37 | gSizer6->Add( m_calc85, 0, wxALL, 5 ); 38 | 39 | m_calc86 = new wxRadioButton( this, wxID_ANY, wxT("TI-86"), wxDefaultPosition, wxDefaultSize, 0 ); 40 | gSizer6->Add( m_calc86, 0, wxALL, 5 ); 41 | 42 | bSizer19->Add( gSizer6, 1, wxEXPAND, 5 ); 43 | 44 | bSizer19->Add( 0, 0, 1, wxEXPAND, 5 ); 45 | 46 | this->SetSizer( bSizer19 ); 47 | this->Layout(); 48 | } 49 | 50 | int WizardCalcTypePage::GetModel() const { 51 | if (m_calc73->GetValue()) { 52 | return TI_73; 53 | } else if (m_calc82->GetValue()) { 54 | return TI_82; 55 | } else if (m_calc83p->GetValue()) { 56 | return TI_83P; 57 | } else if (m_calc83pse->GetValue()) { 58 | return TI_83PSE; 59 | } else if (m_calc84p->GetValue()) { 60 | return TI_84P; 61 | } else if (m_calc84pse->GetValue()) { 62 | return TI_84PSE; 63 | } else if (m_calc85->GetValue()) { 64 | return TI_85; 65 | } else if (m_calc86->GetValue()) { 66 | return TI_86; 67 | } 68 | return -1; 69 | } 70 | 71 | void WizardCalcTypePage::EnableRadios(bool enableRadios) const { 72 | m_calc82->Enable(enableRadios); 73 | m_calc83->Enable(enableRadios); 74 | m_calc85->Enable(enableRadios); 75 | m_calc86->Enable(enableRadios); 76 | } 77 | 78 | wxWizardPage * WizardCalcTypePage::GetPrev() const { 79 | return prev; 80 | } 81 | 82 | wxWizardPage * WizardCalcTypePage::GetNext() const { 83 | return next; 84 | } 85 | -------------------------------------------------------------------------------- /gui/wizard/wizardcalctype.h: -------------------------------------------------------------------------------- 1 | #ifndef WIZARDCALCTYPE_H 2 | #define WIZARDCALCTYPE_H 3 | 4 | #include 5 | #include 6 | #include "calc.h" 7 | 8 | class WizardCalcTypePage : public wxWizardPage 9 | { 10 | private: 11 | LPCALC lpCalc; 12 | protected: 13 | wxStaticText* m_staticText2; 14 | wxRadioButton* m_calc73; 15 | wxRadioButton* m_calc82; 16 | wxRadioButton* m_calc83; 17 | wxRadioButton* m_calc83p; 18 | wxRadioButton* m_calc83pse; 19 | wxRadioButton* m_calc84p; 20 | wxRadioButton* m_calc84pse; 21 | wxRadioButton* m_calc85; 22 | wxRadioButton* m_calc86; 23 | public: 24 | WizardCalcTypePage( wxWizard* parent ); 25 | virtual wxWizardPage *GetNext() const; 26 | virtual wxWizardPage *GetPrev() const; 27 | int GetModel() const; 28 | void EnableRadios(bool enableRadios) const; 29 | wxWizardPage *prev; 30 | wxWizardPage *next; 31 | }; 32 | 33 | #endif 34 | -------------------------------------------------------------------------------- /gui/wizard/wizardos.cpp: -------------------------------------------------------------------------------- 1 | #include "wizardos.h" 2 | #include "gui.h" 3 | 4 | BEGIN_EVENT_TABLE(WizardOSPage, wxWizardPage) 5 | EVT_FILEPICKER_CHANGED(wxID_ANY, WizardOSPage::OnFilePickerChanged) 6 | END_EVENT_TABLE() 7 | 8 | WizardOSPage::WizardOSPage( wxWizard *parent ) : wxWizardPage(parent) 9 | { 10 | wxBoxSizer* bSizer20; 11 | bSizer20 = new wxBoxSizer( wxVERTICAL ); 12 | 13 | m_staticText4 = new wxStaticText( this, wxID_ANY, wxT("A calculator OS file is required to emulate TI calculators."), wxDefaultPosition, wxDefaultSize, 0 ); 14 | m_staticText4->Wrap( 350 ); 15 | bSizer20->Add( m_staticText4, 0, wxALL, 5 ); 16 | 17 | m_staticText5 = new wxStaticText( this, wxID_ANY, wxT("Note that TI has discontinued the ability to automatically download OS updates. If you need a calculator OS file, please download it from their website:"), wxDefaultPosition, wxDefaultSize, 0 ); 18 | m_staticText5->Wrap( 350 ); 19 | bSizer20->Add( m_staticText5, 0, wxALL, 5 ); 20 | 21 | m_hyperlink1 = new wxHyperlinkCtrl( this, wxID_ANY, wxT("Download your OS here"), wxT("https://education.ti.com/en/us/downloads-and-activities"), wxDefaultPosition, wxDefaultSize, wxHL_DEFAULT_STYLE); 22 | bSizer20->Add( m_hyperlink1, 0, wxALL, 5 ); 23 | 24 | m_staticText6 = new wxStaticText( this, wxID_ANY, wxT("Select a calculator OS file:"), wxDefaultPosition, wxDefaultSize, 0 ); 25 | m_staticText6->Wrap( 400 ); 26 | bSizer20->Add( m_staticText6, 0, wxALL, 5 ); 27 | 28 | m_filePicker2 = new wxFilePickerCtrl( this, wxID_ANY, wxEmptyString, wxT("Select a file"), wxT("*.*"), wxDefaultPosition, wxSize( 200,-1 ), wxFLP_DEFAULT_STYLE ); 29 | m_filePicker2->SetMinSize( wxSize( 250,40 ) ); 30 | 31 | bSizer20->Add( m_filePicker2, 0, wxALL, 5 ); 32 | 33 | this->SetSizer( bSizer20 ); 34 | this->Layout(); 35 | } 36 | 37 | bool WizardOSPage::UpdateOSPathState(bool error) { 38 | TIFILE_t *tifile; 39 | bool ready = false; 40 | wxWindow *win = FindWindowById(wxID_FORWARD, GetParent()); 41 | wxMessageDialog *dial; 42 | wxString path = m_filePicker2->GetPath(); 43 | 44 | if (!path.IsEmpty()) { 45 | tifile = newimportvar(path.c_str(), TRUE); 46 | if (tifile == NULL || !((tifile->type == FLASH_TYPE) && (tifile->flash) && (tifile->flash->type == FLASH_TYPE_OS))) { 47 | if (error) { 48 | dial = new wxMessageDialog(NULL, wxT("Invalid OS file specified! Please select a valid OS file, and try again."), 49 | wxT("Error loading OS file"), 50 | wxOK | wxICON_ERROR); 51 | dial->ShowModal(); 52 | } 53 | ready = false; 54 | } else { 55 | ready = true; 56 | } 57 | FreeTiFile(tifile); 58 | } else { 59 | ready = false; 60 | } 61 | 62 | win->Enable(ready); 63 | return ready; 64 | } 65 | 66 | void WizardOSPage::OnFilePickerChanged(wxFileDirPickerEvent &event) { 67 | this->UpdateOSPathState(true); 68 | } 69 | 70 | wxWizardPage * WizardOSPage::GetPrev() const { 71 | return prev; 72 | } 73 | 74 | wxWizardPage * WizardOSPage::GetNext() const { 75 | if (creatingROM) { 76 | return NULL; 77 | } 78 | return next; 79 | } 80 | -------------------------------------------------------------------------------- /gui/wizard/wizardos.h: -------------------------------------------------------------------------------- 1 | #ifndef WIZARDOS_H 2 | #define WIZARDOS_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | class WizardOSPage : public wxWizardPage 10 | { 11 | private: 12 | wxStaticText* m_staticText4; 13 | wxStaticText* m_staticText5; 14 | wxStaticText* m_staticText6; 15 | wxHyperlinkCtrl* m_hyperlink1; 16 | void OnFilePickerChanged(wxFileDirPickerEvent &); 17 | protected: 18 | DECLARE_EVENT_TABLE() 19 | public: 20 | WizardOSPage( wxWizard* parent ); 21 | virtual wxWizardPage *GetNext() const; 22 | virtual wxWizardPage *GetPrev() const; 23 | bool UpdateOSPathState(bool error = false); 24 | //TOOD: make getters and setters 25 | wxWizardPage *prev; 26 | wxWizardPage *next; 27 | int model; 28 | bool creatingROM; 29 | wxFilePickerCtrl* m_filePicker2; 30 | }; 31 | 32 | 33 | #endif 34 | -------------------------------------------------------------------------------- /gui/wizard/wizardstart.cpp: -------------------------------------------------------------------------------- 1 | #include "wizardstart.h" 2 | #include "gui.h" 3 | #include "var.h" 4 | 5 | BEGIN_EVENT_TABLE(WizardStartPage, wxWizardPage) 6 | EVT_RADIOBUTTON(wxID_ANY, WizardStartPage::OnRadioSelected) 7 | EVT_FILEPICKER_CHANGED(wxID_ANY, WizardStartPage::OnFileChanged) 8 | END_EVENT_TABLE() 9 | 10 | WizardStartPage::WizardStartPage( wxWizard* parent) : wxWizardPage( parent ) 11 | { 12 | wxBoxSizer* bSizer18; 13 | bSizer18 = new wxBoxSizer( wxVERTICAL ); 14 | 15 | m_staticText1 = new wxStaticText( this, wxID_ANY, wxT("This wizard will guide you through running Wabbitemu for the first time.\n\n A ROM is required to emulate TI calculators. How do you want to get a ROM image for Wabbitemu?"), wxDefaultPosition, wxDefaultSize, 0 ); 16 | m_staticText1->Wrap(400); 17 | bSizer18->Add( m_staticText1, 0, wxALL, 5 ); 18 | 19 | m_browseRadio = new wxRadioButton( this, wxID_ANY, wxT("Browse for a ROM image on my computer"), wxDefaultPosition, wxDefaultSize, wxRB_GROUP ); 20 | bSizer18->Add( m_browseRadio, 0, wxALL, 5 ); 21 | 22 | m_filePicker1 = new wxFilePickerCtrl( this, wxID_ANY, wxT("."), wxT("Browse for a ROM image"), wxT("All known files|*.rom;*.sav|ROM images|*.rom|Savestate images|*.sav"), wxDefaultPosition, wxSize( 300,-1 ), wxFLP_DEFAULT_STYLE ); 23 | m_filePicker1->SetMinSize( wxSize( 300,30 ) ); 24 | 25 | bSizer18->Add( m_filePicker1, 0, wxALL, 5 ); 26 | 27 | m_copyRadio = new wxRadioButton( this, wxID_ANY, wxT("Copy a ROM image from a real calculator"), wxDefaultPosition, wxDefaultSize, 0 ); 28 | bSizer18->Add( m_copyRadio, 0, wxALL, 5 ); 29 | 30 | m_createRadio = new wxRadioButton( this, wxID_ANY, wxT("Create a ROM image using open source software"), wxDefaultPosition, wxDefaultSize, 0 ); 31 | bSizer18->Add( m_createRadio, 0, wxALL, 5 ); 32 | 33 | this->SetSizer( bSizer18 ); 34 | this->Layout(); 35 | 36 | // Disable ROM copy (we don't have that implemented yet) 37 | m_copyRadio->Enable(false); 38 | } 39 | 40 | bool WizardStartPage::UpdateROMPathState(bool error) { 41 | TIFILE_t *tifile; 42 | bool ready = false; 43 | wxWindow *win = FindWindowById(wxID_FORWARD, GetParent()); 44 | wxMessageDialog *dial; 45 | wxString path = m_filePicker1->GetPath(); 46 | 47 | if (!path.IsEmpty()) { 48 | tifile = newimportvar(path.c_str(), TRUE); 49 | if (tifile == NULL || !((tifile->type == ROM_TYPE) || (tifile->type == SAV_TYPE))) { 50 | if (error) { 51 | dial = new wxMessageDialog(NULL, wxT("Invalid ROM image specified! Please select a valid ROM image, and try again."), 52 | wxT("Error loading ROM image"), 53 | wxOK | wxICON_ERROR); 54 | dial->ShowModal(); 55 | } 56 | ready = false; 57 | } else { 58 | ready = true; 59 | } 60 | FreeTiFile(tifile); 61 | } else { 62 | ready = false; 63 | } 64 | 65 | win->Enable(ready); 66 | return ready; 67 | } 68 | 69 | void WizardStartPage::OnFileChanged(wxFileDirPickerEvent &event) { 70 | this->UpdateROMPathState(true); 71 | } 72 | 73 | void WizardStartPage::OnRadioSelected(wxCommandEvent &event) { 74 | wxWindow *win = FindWindowById(wxID_FORWARD, GetParent()); 75 | wxMessageDialog *dial; 76 | if (m_browseRadio->GetValue()) { 77 | win->SetLabel(wxT("Finish")); 78 | this->UpdateROMPathState(); 79 | m_filePicker1->Enable(true); 80 | return; 81 | } 82 | win->SetLabel(wxT("Next >")); 83 | win->Enable(true); 84 | m_filePicker1->Enable(false); 85 | } 86 | 87 | wxWizardPage * WizardStartPage::GetPrev() const { 88 | return NULL; 89 | } 90 | 91 | wxWizardPage * WizardStartPage::GetNext() const { 92 | if (m_browseRadio->GetValue()) { 93 | return NULL; 94 | } 95 | return next; 96 | } 97 | -------------------------------------------------------------------------------- /gui/wizard/wizardstart.h: -------------------------------------------------------------------------------- 1 | #ifndef WIZARDSTART_H 2 | #define WIZARDSTART_H 3 | 4 | #include 5 | #include 6 | #include 7 | #include "calc.h" 8 | 9 | class WizardStartPage : public wxWizardPage 10 | { 11 | private: 12 | void OnRadioSelected(wxCommandEvent &); 13 | void OnFileChanged(wxFileDirPickerEvent &); 14 | void OnFinished(wxWizardEvent &); 15 | protected: 16 | wxStaticText* m_staticText1; 17 | DECLARE_EVENT_TABLE() 18 | public: 19 | WizardStartPage( wxWizard* parent ); 20 | virtual wxWizardPage *GetNext() const; 21 | virtual wxWizardPage *GetPrev() const; 22 | bool UpdateROMPathState(bool error = false); 23 | //TODO: make getters and setters 24 | wxRadioButton* m_browseRadio; 25 | wxRadioButton* m_createRadio; 26 | wxRadioButton* m_copyRadio; 27 | wxFilePickerCtrl* m_filePicker1; 28 | wxWizardPage *next; 29 | LPCALC lpCalc; 30 | }; 31 | 32 | #endif 33 | -------------------------------------------------------------------------------- /hardware/81hw.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #include "81hw.h" 4 | #include "lcd.h" 5 | #include "keys.h" 6 | #include "device.h" 7 | #include "calc.h" 8 | 9 | static void port10(CPU_t *cpu, device_t *dev); 10 | static double timer_freq81[4] = { 1.0 / 800.0, 1.0 / 400.0, 3.0 / 800.0, 1.0 / 200.0 }; 11 | 12 | // 81 screen offset 13 | static void port0(CPU_t *cpu, device_t *dev) { 14 | if (cpu->input) { 15 | cpu->bus = 0; 16 | cpu->input = FALSE; 17 | } else if (cpu->output) { 18 | dev->aux = (LPVOID) (0x100 * ((cpu->bus % 0x20) + 0xE0)); 19 | cpu->pio.devices[0x10].aux = dev->aux; 20 | port10(cpu, dev); 21 | cpu->output = FALSE; 22 | device_t devt; 23 | devt.aux = cpu->pio.lcd; 24 | LCD_data(cpu, &devt); 25 | } 26 | return; 27 | } 28 | 29 | // Contrast v1.x 30 | static void port2(CPU_t *cpu, device_t *dev) { 31 | LCD_t *lcd = (LCD_t *) dev->aux; 32 | if (cpu->input) { 33 | cpu->input = FALSE; 34 | } else if (cpu->output) { 35 | //HACK: still not sure exactly how this works :P 36 | lcd->contrast = lcd->base_level - 19 + cpu->bus; 37 | if (lcd->contrast > 64) 38 | lcd->contrast = 64; 39 | cpu->output = FALSE; 40 | } 41 | return; 42 | } 43 | 44 | static void port3(CPU_t *cpu, device_t *dev) { 45 | STDINT_t * stdint = (STDINT_t *) dev->aux; 46 | 47 | if (cpu->input) { 48 | unsigned char result = 0; 49 | if ((tc_elapsed(cpu->timer_c) - stdint->lastchk1) > stdint->timermax1) result += 4; 50 | if (cpu->pio.lcd->active) result += 2; 51 | if (stdint->on_latch) result += 1; 52 | else result += 8; 53 | 54 | cpu->bus = result; 55 | cpu->input = FALSE; 56 | } else if (cpu->output) { 57 | if (cpu->bus & 0x08) { 58 | cpu->pio.lcd->active = TRUE; //I'm worried about this 59 | } else { 60 | cpu->pio.lcd->active = FALSE; 61 | } 62 | 63 | if ((cpu->bus & 0x01) == 0) 64 | stdint->on_latch = FALSE; 65 | 66 | stdint->intactive = cpu->bus; 67 | cpu->output = FALSE; 68 | } 69 | 70 | if (!(stdint->intactive & 0x04) && cpu->pio.lcd->active == TRUE) { 71 | if ((tc_elapsed(cpu->timer_c) - stdint->lastchk1) > stdint->timermax1) { 72 | cpu->interrupt = TRUE; 73 | while ((tc_elapsed(cpu->timer_c) - stdint->lastchk1) > stdint->timermax1) 74 | stdint->lastchk1 += stdint->timermax1; 75 | } 76 | } 77 | 78 | if ((stdint->intactive & 0x01) && (cpu->pio.keypad->on_pressed & KEY_VALUE_MASK) && (stdint->on_backup & KEY_VALUE_MASK) == 0) { 79 | stdint->on_latch = TRUE; 80 | } 81 | stdint->on_backup = cpu->pio.keypad->on_pressed; 82 | if (stdint->on_latch) 83 | cpu->interrupt = TRUE; 84 | } 85 | 86 | static void port4(CPU_t *cpu, device_t *dev) { 87 | if (cpu->input) { 88 | cpu->bus = 0x00; 89 | cpu->input = FALSE; 90 | } else if (cpu->output) { 91 | cpu->output = FALSE; 92 | dev->aux = (void *) cpu->bus; 93 | int freq = (cpu->bus >> 1) & 0x3; 94 | cpu->pio.stdint->timermax1 = cpu->pio.stdint->freq[freq]; 95 | cpu->pio.stdint->lastchk1 = tc_elapsed(cpu->timer_c); 96 | int lcd_mode = (cpu->bus >> 3) & 0x3; 97 | if (lcd_mode == 0) { 98 | cpu->pio.lcd->width = 80; 99 | } else { 100 | cpu->pio.lcd->width = 32 * lcd_mode + 64; 101 | } 102 | 103 | 104 | cpu->output = FALSE; 105 | } 106 | } 107 | 108 | static void port5(CPU_t *cpu, device_t *dev) { 109 | if (cpu->input) { 110 | cpu->bus = 0x00; 111 | cpu->input = FALSE; 112 | } else if (cpu->output) { 113 | cpu->output = FALSE; 114 | } 115 | } 116 | 117 | static void port6(CPU_t *cpu, device_t *dev) { 118 | if (cpu->input) { 119 | cpu->bus = 0x00; 120 | cpu->input = FALSE; 121 | } else if (cpu->output) { 122 | cpu->output = FALSE; 123 | } 124 | } 125 | 126 | static void port10(CPU_t *cpu, device_t *dev) { 127 | size_t screen_addr = (size_t) dev->aux; 128 | // Output the entire LCD 129 | LCD_t *lcd = cpu->pio.lcd; 130 | unsigned char *base_addr = cpu->mem_c->banks[mc_bank(screen_addr)].addr + mc_base(screen_addr); 131 | int k = 0, l = 0; 132 | for (int j = 0; j < 64; j++) { 133 | for (int i = 0; i < 12; i++, k++, l++) { 134 | lcd->display[k] = *(base_addr + l); 135 | } 136 | k += 4; 137 | } 138 | } 139 | 140 | static STDINT_t* INT81_init(CPU_t* cpu) { 141 | STDINT_t * stdint = (STDINT_t *) malloc(sizeof(STDINT_t)); 142 | if (!stdint) { 143 | printf("Couldn't allocate memory for standard interrupt\n"); 144 | return NULL; 145 | } 146 | 147 | memcpy(stdint->freq, timer_freq81, 4 * sizeof(stdint->freq[0])); 148 | 149 | stdint->intactive = 0; 150 | stdint->timermax1 = stdint->freq[3]; 151 | stdint->lastchk1 = tc_elapsed(cpu->timer_c); 152 | stdint->on_backup = 0; 153 | stdint->on_latch = FALSE; 154 | return stdint; 155 | } 156 | 157 | int memory_init_81(memc *mc) { 158 | memset(mc, 0, sizeof(memory_context_t)); 159 | 160 | mc->mem_read_break_callback = mem_debug_callback; 161 | mc->mem_write_break_callback = mem_debug_callback; 162 | #ifdef WINVER 163 | mc->breakpoint_manager_callback = check_break_callback; 164 | #endif 165 | 166 | /* Set Number of Pages here */ 167 | mc->flash_pages = 2; 168 | mc->ram_pages = 2; 169 | 170 | mc->flash_version = 1; 171 | mc->flash_size = mc->flash_pages * PAGE_SIZE; 172 | mc->flash = (unsigned char *) calloc(mc->flash_pages, PAGE_SIZE); 173 | mc->flash_break = (unsigned char *) calloc(mc->flash_pages, PAGE_SIZE); 174 | memset(mc->flash, 0xFF, mc->flash_size); 175 | 176 | mc->ram_size = mc->ram_pages * PAGE_SIZE; 177 | mc->ram = (unsigned char *)calloc(mc->ram_pages, PAGE_SIZE); 178 | mc->ram_break = (unsigned char *) calloc(mc->ram_pages, PAGE_SIZE); 179 | 180 | if (!mc->flash || !mc->ram) { 181 | return 1; 182 | } 183 | 184 | mc->boot_mapped = FALSE; 185 | mc->flash_locked = TRUE; 186 | 187 | /* Organize bank states here */ 188 | 189 | /* Address page write? ram? no exec? */ 190 | bank_state_t banks[5] = { 191 | {mc->flash, 0, FALSE, FALSE, FALSE}, 192 | {mc->flash+0x1*PAGE_SIZE, 0x1, FALSE, FALSE, FALSE}, 193 | {mc->flash+0x1*PAGE_SIZE, 0x1, FALSE, FALSE, FALSE}, 194 | {mc->ram, 0, FALSE, TRUE, FALSE}, 195 | {NULL, 0, FALSE, FALSE, FALSE} 196 | }; 197 | 198 | memcpy(mc->normal_banks, banks, sizeof(banks)); 199 | mc->banks = mc->normal_banks; 200 | return 0; 201 | } 202 | 203 | int device_init_81(CPU_t *cpu) { 204 | ClearDevices(cpu); 205 | 206 | LCD_t *lcd = LCD_init(cpu, TI_81); 207 | cpu->pio.devices[0x00].active = TRUE; 208 | cpu->pio.devices[0x00].aux = NULL; 209 | cpu->pio.devices[0x00].code = (devp) &port0; 210 | 211 | keypad_t *keyp = keypad_init(cpu); 212 | cpu->pio.devices[0x01].active = TRUE; 213 | cpu->pio.devices[0x01].aux = keyp; 214 | cpu->pio.devices[0x01].code = (devp) &keypad; 215 | 216 | cpu->pio.devices[0x02].active = TRUE; 217 | cpu->pio.devices[0x02].code = (devp) &port2; 218 | cpu->pio.devices[0x02].aux = lcd; 219 | 220 | STDINT_t *stdint = INT81_init(cpu); 221 | cpu->pio.devices[0x03].active = TRUE; 222 | cpu->pio.devices[0x03].aux = stdint; 223 | cpu->pio.devices[0x03].code = (devp) &port3; 224 | 225 | cpu->pio.devices[0x04].active = TRUE; 226 | cpu->pio.devices[0x04].code = (devp) &port4; 227 | cpu->pio.devices[0x04].aux = lcd; 228 | 229 | cpu->pio.devices[0x05].active = TRUE; 230 | cpu->pio.devices[0x05].code = (devp) &port5; 231 | 232 | cpu->pio.devices[0x06].active = TRUE; 233 | cpu->pio.devices[0x06].code = (devp) &port6; 234 | 235 | cpu->pio.devices[0x10].active = TRUE; 236 | cpu->pio.devices[0x10].aux = NULL; 237 | cpu->pio.devices[0x10].code = (devp) &port10; 238 | 239 | cpu->pio.devices[0x11].active = TRUE; 240 | cpu->pio.devices[0x11].aux = lcd; 241 | cpu->pio.devices[0x11].code = (devp) &LCD_data; 242 | 243 | cpu->pio.lcd = lcd; 244 | cpu->pio.keypad = keyp; 245 | cpu->pio.link = NULL; 246 | cpu->pio.stdint = stdint; 247 | cpu->pio.se_aux = NULL; 248 | cpu->pio.model = TI_81; 249 | 250 | //Append_interrupt_device(cpu, 0x00, 1); 251 | Append_interrupt_device(cpu, 0x03, 1); 252 | Append_interrupt_device(cpu, 0x10, 16000); 253 | Append_interrupt_device(cpu, 0x11, 16000); 254 | //Append_interrupt_device(cpu, 0x11, 128); 255 | return 0; 256 | } 257 | -------------------------------------------------------------------------------- /hardware/81hw.h: -------------------------------------------------------------------------------- 1 | #ifndef TI81HW_H 2 | #define TI81HW_H 3 | #include "core.h" 4 | #include "ti_stdint.h" 5 | 6 | #define NumElm(array) (sizeof (array) / sizeof ((array)[0])) 7 | 8 | int device_init_81(CPU_t*); 9 | int memory_init_81(memc *); 10 | 11 | #endif 12 | -------------------------------------------------------------------------------- /hardware/83hw.h: -------------------------------------------------------------------------------- 1 | #ifndef TI83HW_H 2 | #define TI83HW_H 3 | #include "core.h" 4 | #include "ti_stdint.h" 5 | 6 | #define PAGE_SIZE 16384 7 | 8 | 9 | #define NumElm(array) (sizeof (array) / sizeof ((array)[0])) 10 | 11 | 12 | 13 | STDINT_t* INT83_init(CPU_t*); 14 | int device_init_83(CPU_t*,int); 15 | int memory_init_83(memc *); 16 | 17 | void port0_83(CPU_t *, device_t *); 18 | void port2_83(CPU_t *, device_t *); 19 | void port3_83(CPU_t *, device_t *); 20 | void port4_83(CPU_t *, device_t *); 21 | void port6_83(CPU_t *, device_t *); 22 | void port7_83(CPU_t *, device_t *); 23 | void port14_83(CPU_t *, device_t *); 24 | 25 | 26 | #endif 27 | -------------------------------------------------------------------------------- /hardware/83phw.h: -------------------------------------------------------------------------------- 1 | #ifndef TI83PHW_H 2 | #define TI83PHW_H 3 | #include "core.h" 4 | #include "ti_stdint.h" 5 | 6 | #ifndef LINK_READ 7 | #define LINK_READ 8 | #define LinkRead (((cpu->pio.link->host & 0x03) | (cpu->pio.link->client[0] & 0x03)) ^ 3) 9 | #endif 10 | #define NumElm(array) (sizeof (array) / sizeof ((array)[0])) 11 | 12 | int device_init_83p(CPU_t*); 13 | int memory_init_83p(memc *); 14 | 15 | #endif 16 | -------------------------------------------------------------------------------- /hardware/83psehw.h: -------------------------------------------------------------------------------- 1 | #ifndef TI83PSEHW_H 2 | #define TI83PSEHW_H 3 | #include "core.h" 4 | #include "ti_stdint.h" 5 | 6 | #ifndef LINK_READ 7 | #define LINK_READ 8 | #define LinkRead (((cpu->pio.link->host & 0x03) | (cpu->pio.link->client[0] & 0x03))^3) 9 | #endif 10 | #define NumElm(array) (sizeof (array) / sizeof ((array)[0])) 11 | 12 | typedef struct TIMER { 13 | /* determines which clock if any is used for time */ 14 | unsigned long long lastTstates; 15 | double lastTicks; 16 | double divsor; 17 | BOOL loop; 18 | BOOL interrupt; 19 | BOOL underflow; 20 | BOOL generate; 21 | BOOL active; 22 | unsigned char clock; 23 | unsigned char count; 24 | unsigned char max; 25 | } TIMER_t; 26 | 27 | typedef struct XTAL { 28 | double lastTime; /* actual real time of last tick */ 29 | unsigned long long ticks; /* ticks of the xtal timer */ 30 | TIMER_t timers[3]; 31 | } XTAL_t; 32 | 33 | typedef struct LINKASSIST { 34 | unsigned char link_enable; 35 | unsigned char in; 36 | unsigned char out; 37 | unsigned char working; 38 | BOOL receiving; 39 | BOOL read; 40 | BOOL ready; 41 | BOOL error; 42 | BOOL sending; 43 | double last_access; 44 | int bit; 45 | } LINKASSIST_t; 46 | 47 | typedef struct MD5 { 48 | /* 32 bit registers */ 49 | union { 50 | struct { 51 | uint32_t a; 52 | uint32_t b; 53 | uint32_t c; 54 | uint32_t d; 55 | uint32_t x; 56 | uint32_t ac; 57 | }; 58 | uint32_t reg[6]; 59 | }; 60 | uint8_t s; 61 | uint8_t mode ; 62 | } MD5_t; 63 | 64 | typedef struct DELAY { 65 | union { 66 | struct { 67 | unsigned char lcd1; 68 | unsigned char lcd2; 69 | unsigned char lcd3; 70 | unsigned char lcd4; 71 | unsigned char unkown; 72 | unsigned char mad; /*memory access delay*/ 73 | unsigned char lcdwait; 74 | }; 75 | unsigned char reg[7]; 76 | }; 77 | } DELAY_t; 78 | 79 | typedef struct CLOCK { 80 | unsigned char enable; 81 | unsigned long set; 82 | unsigned long base; 83 | double lasttime; 84 | } CLOCK_t; 85 | 86 | typedef struct USB { 87 | unsigned int USBLineState; //Whether each line is low or high 88 | unsigned int USBEvents; //Whether interrupts have occurred 89 | unsigned int USBEventMask; //Whether interrupts should be generated when USB lines change 90 | BOOL LineInterrupt; 91 | BOOL ProtocolInterrupt; 92 | BOOL ProtocolInterruptEnabled; 93 | unsigned int DevAddress; //Current USB device address 94 | int version; 95 | BOOL USBPowered; 96 | 97 | 98 | unsigned char Port4A; 99 | unsigned char Port4C; 100 | unsigned char Port54; 101 | } USB_t; 102 | 103 | enum USB_MASK { 104 | DPLUS_LOW_MASK = 0x01, 105 | DPLUS_HIGH_MASK = 0x02, 106 | DMINUS_LOW_MASK = 0x04, 107 | DMINUS_HIGH_MASK = 0x08, 108 | ID_LOW_MASK = 0x10, 109 | ID_HIGH_MASK = 0x20, 110 | VBUS_HIGH_MASK = 0x40, 111 | VBUS_LOW_MASK = 0x80, 112 | }; 113 | 114 | typedef struct SE_AUX { 115 | CLOCK_t clock; 116 | DELAY_t delay; 117 | MD5_t md5; 118 | LINKASSIST_t linka; 119 | XTAL_t xtal; 120 | USB_t usb; 121 | int model_bits; 122 | } SE_AUX_t; 123 | 124 | STDINT_t *INT83PSE_init(CPU_t*); 125 | int device_init_83pse(CPU_t*); 126 | int memory_init_83pse(memc *); 127 | int memory_init_84p(memc *); 128 | 129 | void port0_83pse(CPU_t *, device_t *); 130 | void port2_83pse(CPU_t *, device_t *); 131 | void port3_83pse(CPU_t *, device_t *); 132 | void port4_83pse(CPU_t *, device_t *); 133 | void port6_83pse(CPU_t *, device_t *); 134 | void port7_83pse(CPU_t *, device_t *); 135 | void port14_83pse(CPU_t *, device_t *); 136 | int GetCPUSpeed(CPU_t *); 137 | 138 | #endif 139 | -------------------------------------------------------------------------------- /hardware/86hw.h: -------------------------------------------------------------------------------- 1 | #ifndef _86HW_H_ 2 | #define _86HW_H_ 3 | 4 | #include "ti_stdint.h" 5 | 6 | int device_init_86(CPU_t*); 7 | int memory_init_86(memc *); 8 | 9 | #endif /*86HW_H_*/ 10 | -------------------------------------------------------------------------------- /hardware/keys.h: -------------------------------------------------------------------------------- 1 | #ifndef KEYS_H 2 | #define KEYS_H 3 | #include "core.h" 4 | 5 | typedef struct keypad { 6 | unsigned char group; 7 | unsigned char keys[8][8], on_pressed; 8 | unsigned long long last_pressed[8][8], on_last_pressed; 9 | } keypad_t; 10 | 11 | typedef struct KEYPROG { 12 | int vk; 13 | int group; 14 | int bit; 15 | } keyprog_t; 16 | 17 | //shhh..Redefine for sake of ease 18 | #define VKF_EQUAL 0xBB 19 | #define VKF_COMMA 0xBC 20 | #define VKF_MINUS 0xBD 21 | #define VKF_PERIOD 0xBE 22 | #define VKF_LBRACKET 0xDB 23 | #define VKF_RBRACKET 0xDD 24 | #define VKF_QUOTE 0xDE 25 | #define WXK_LSHIFT WXK_SPECIAL20+1 26 | #define WXK_RSHIFT WXK_LSHIFT+1 27 | 28 | 29 | keypad_t *keypad_init(CPU_t*); 30 | void keypad(CPU_t *, device_t *); 31 | 32 | keyprog_t *keypad_key_press(CPU_t*, unsigned int vk, BOOL *changed = NULL); 33 | keyprog_t *keypad_key_release(CPU_t*, unsigned int vk); 34 | void keypad_press(CPU_t *cpu, int group, int bit); 35 | void keypad_release(CPU_t *cpu, int group, int bit); 36 | 37 | #ifdef WINVER 38 | //used by the debugger to fix stuck keys 39 | void keypad_vk_release(HWND hwnd, int group, int bit); 40 | #endif 41 | 42 | #define KEY_VALUE_MASK (0x0F) 43 | 44 | #define KEY_KEYBOARDPRESS 0x01 45 | #define KEY_MOUSEPRESS 0x02 46 | #define KEY_LOCKPRESS 0x04 47 | #define KEY_FALSEPRESS 0x08 48 | #define KEY_STATEDOWN 0x10 49 | 50 | #define KEYGROUP_ON 0x05 51 | #define KEYBIT_ON 0x00 52 | 53 | #define NumElm(array) (sizeof (array) / sizeof ((array)[0])) 54 | 55 | #endif /*#ifndef KEYS_H*/ 56 | -------------------------------------------------------------------------------- /hardware/lcd.h: -------------------------------------------------------------------------------- 1 | #ifndef LCD_H 2 | #define LCD_H 3 | 4 | #include "core.h" 5 | 6 | #define STEADY_FREQ_MIN 30 7 | #define STEADY_FREQ_MAX 120 8 | 9 | /* 10 | * LCD dimensions 11 | * Large enough to encompass all z80 models 12 | */ 13 | #define LCD_HEIGHT 64 14 | #define LCD_WIDTH 128 15 | #define LCD_MEM_WIDTH (LCD_WIDTH / 8) 16 | // One bit per pixel 17 | #define DISPLAY_SIZE (LCD_MEM_WIDTH * LCD_HEIGHT) 18 | // One byte per pixel 19 | #define GRAY_DISPLAY_SIZE (DISPLAY_SIZE * 8) 20 | // Frames to spread gray generation over 21 | #define LCD_GRAY_SPREAD 6.0 22 | 23 | /* 24 | * Maximum shades the LCD will be able to 25 | * render. Actual shades rendered is stored 26 | * in LCD.shades. The default value is also 27 | * specified (generates a good image for 28 | * perfect gray mode) 29 | */ 30 | #define LCD_MAX_SHADES 12 31 | #define LCD_DEFAULT_SHADES 6 32 | 33 | /* 34 | * Cursor mode describes the 4 35 | * directions the cursor can be in. 36 | */ 37 | typedef enum _LCD_CURSOR_MODE { 38 | X_DOWN = 0, 39 | X_UP = 1, 40 | Y_DOWN = 2, 41 | Y_UP = 3, 42 | MODE_NONE = 4, 43 | } LCD_CURSOR_MODE; 44 | 45 | /* 46 | * Modes describing how the LCD images are generated. 47 | * Perfect gray attempts to use full LCD images to generate 48 | * a grayscale image. 49 | * Steady mode captures at timed intervals and doesn't rely 50 | * on the LCD screen being updated to generate its images. 51 | */ 52 | typedef enum _LCD_MODE { 53 | MODE_PERFECT_GRAY = 0, // Special grayscale mode 54 | MODE_STEADY, // Steady frame capture mode 55 | MODE_GAME_GRAY, 56 | } LCD_MODE; 57 | 58 | 59 | /* Main structure describing all attributes specific to one LCD, 60 | * additionally calculation buffers (such as screen) are stored 61 | * here to prevent thread related issues with a static buffer 62 | */ 63 | typedef struct LCD { 64 | void (*free)(struct LCD*); // Function to free this aux 65 | BOOL active; // TRUE = on, FALSE = off 66 | u_int word_len; 67 | int x, y, z; /* LCD cursors */ 68 | int width; 69 | u_int lcd_delay; //delay in tstate required to write 70 | 71 | LCD_CURSOR_MODE cursor_mode; /* Y_UP, Y_DOWN, X_UP, X_DOWN */ 72 | u_int last_read; /* Buffer previous read */ 73 | u_int contrast; /* 0 to 63 */ 74 | u_int base_level; /* used in lcd level to handle contrast */ 75 | uint8_t display[DISPLAY_SIZE]; /* LCD display memory */ 76 | uint8_t screen[LCD_HEIGHT][LCD_WIDTH]; 77 | int front; 78 | uint8_t queue[LCD_MAX_SHADES][DISPLAY_SIZE];/* holds previous buffers for grey */ 79 | uint8_t gif[LCD_HEIGHT*2][LCD_WIDTH*2]; /*for rendering limited color gifs*/ 80 | u_int shades; /* number of shades of grey*/ 81 | LCD_MODE mode; /* Mode of LCD rendering */ 82 | double steady_frame; /* Length of a steady frame in seconds */ 83 | double time; /* Last lcd update in seconds*/ 84 | double ufps, ufps_last; /* User frames per second*/ 85 | double lastgifframe; 86 | double write_avg, write_last; /* Used to determine freq. of writes to the LCD */ 87 | long long last_tstate; // timer_c->tstate of the last write 88 | } LCD_t; 89 | 90 | /* Device functions */ 91 | LCD_t *LCD_init(CPU_t *, int); 92 | void LCD_timer_refresh(CPU_t *); 93 | void LCD_command(CPU_t *, device_t *); 94 | void LCD_data(CPU_t *, device_t *); 95 | 96 | /* Interface functions */ 97 | uint8_t *LCD_image(LCD_t *); 98 | 99 | #endif /* #ifndef LCD_H */ 100 | -------------------------------------------------------------------------------- /hardware/link.h: -------------------------------------------------------------------------------- 1 | #ifndef LINK_H 2 | #define LINK_H 3 | #include "core.h" // CPU_t 4 | 5 | #ifdef WINVER 6 | #include "sound.h" // audio_t 7 | #endif 8 | 9 | #include "var.h" 10 | #include "state.h" 11 | 12 | // Link timing 13 | #define LINK_DELAY 100 /* Delay between commands */ 14 | #define LINK_GARBAGE_DELAY (14 * MHZ_6) /* Delay for oncalc garbage collector */ 15 | #define LINK_TIMEOUT (2 * MHZ_6) /* Maximum time given to respond per bit */ 16 | #define LINK_STEP 10 /* cycles between link status checks */ 17 | 18 | // Link errors 19 | typedef enum { 20 | LERR_SUCCESS = 0, /* No error */ 21 | LERR_LINK = 1, /* General link error */ 22 | LERR_TIMEOUT, /* Time out error */ 23 | LERR_FORCELOAD, /* Error force loading an application (TI-83+) */ 24 | LERR_CHKSUM, /* Packet with invalid checksum was received */ 25 | LERR_NOTINIT, /* Link was not initialized */ 26 | LERR_MEM, /* Not enough memory on calc */ 27 | LERR_MODEL, /* Not the correct model for file */ 28 | LERR_FILE, /* Invalid TIFILE in argument */ 29 | LERR_SYSTEM /* Something wrong in wabbitemu */ 30 | } LINK_ERR; 31 | 32 | // Destination flags 33 | typedef enum SEND_FLAG { 34 | SEND_CUR, /* sends based on current flag settings */ 35 | SEND_RAM, /* sends to RAM, regardless of flag settings */ 36 | SEND_ARC /* sends to archive, regardless of flag settings */ 37 | } SEND_FLAG; 38 | 39 | typedef enum { 40 | CID_VAR = 0x06, /* Request variable header */ 41 | CID_CTS = 0x09, /* Clear to send */ 42 | CID_DATA = 0x15, 43 | CID_VER = 0x2D, 44 | CID_EXIT = 0x36, 45 | CID_ACK = 0x56, 46 | CID_ERR = 0x5A, 47 | CID_RDY = 0x68, 48 | CID_SCR = 0x6D, 49 | CID_DEL = 0x88, 50 | CID_EOT = 0x92, 51 | CID_REQ = 0xA2, 52 | CID_RTS = 0xC9 53 | } LINK_COMMAND_ID; 54 | 55 | /* Contains connections and current state 56 | * of a link port. */ 57 | typedef struct link { 58 | u_char host; // what we wrote to the link port 59 | u_char *client; // what they wrote to the link port 60 | volatile size_t vlink_send; // amount already sent over vlink 61 | volatile size_t vlink_recv; // amount already received over the link 62 | size_t vlink_size; // Size of the var currently on the link (if known) 63 | #ifdef WINVER 64 | AUDIO_t audio; 65 | #endif 66 | BYTE vout; 67 | LPBYTE vin; // Virtual Link data 68 | BOOL hasChanged; // if were connected to a hub, has the hub value changed 69 | unsigned long long changedTime; // when the data changed 70 | } link_t; 71 | 72 | #pragma pack(push, 1) 73 | 74 | /* Header for packets send over the link */ 75 | typedef struct _TI_PKTHDR { 76 | uint8_t machine_ID; /* corresponds to a particular device */ 77 | uint8_t command_ID; /* specifies the format of the rest of the pkt */ 78 | uint16_t data_len; /* optional field */ 79 | } TI_PKTHDR; 80 | 81 | typedef struct { 82 | uint8_t size; 83 | uint16_t address; 84 | uint8_t type; 85 | uint8_t data[256]; 86 | uint8_t chksum; 87 | } intelhex_t; 88 | 89 | /* Header describing variable that is 90 | * to send or received over the link */ 91 | typedef struct _TI_VARHDR { 92 | uint16_t length; // datalength not including the header 93 | uint8_t type_ID; // specifies type of variable 94 | union { 95 | struct { 96 | char name[8]; 97 | uint8_t version; 98 | }; 99 | struct { 100 | uint8_t name_length; 101 | char name86[8]; 102 | }; 103 | }; 104 | uint8_t type_ID2; 105 | } TI_VARHDR; 106 | 107 | /* Header describing the flash application 108 | * sent or received over the link */ 109 | typedef struct _TI_FLASHHDR { 110 | uint16_t sizeLSB; 111 | uint8_t type_ID; 112 | uint16_t sizeMSB; 113 | uint8_t flag; 114 | uint16_t offset; 115 | uint16_t page; 116 | } TI_FLASHHDR; 117 | 118 | typedef struct _TI_BACKUPHDR { 119 | uint16_t flags_size; 120 | uint8_t type_ID; 121 | uint16_t data_size; 122 | uint16_t symbol_size; 123 | uint16_t user_addr; 124 | } TI_BACKUPHDR; 125 | 126 | #pragma pack(pop) 127 | 128 | typedef struct _TI_DATA { 129 | uint16_t length; 130 | void *data; 131 | } TI_DATA; 132 | 133 | enum TI83POBJ { 134 | RealObj = 0x00, 135 | ListObj = 0x01, 136 | MatObj = 0x02, 137 | EquObj = 0x03, 138 | StrngObj = 0x04, 139 | ProgObj = 0x05, 140 | ProtProgObj = 0x06, 141 | PictObj = 0x07, 142 | GDBObj = 0x08, 143 | UnknownObj = 0x09, 144 | UnknownEquObj = 0x0A, 145 | NewEquObj = 0x0B, 146 | CplxObj = 0x0C, 147 | CListObj = 0x0D, 148 | UndefObj = 0x0E, 149 | WindowObj = 0x0F, 150 | BackupObj_82 = 0x0F, 151 | ZStoObj = 0x10, 152 | TblRngObj = 0x11, 153 | LCDObj = 0x12, 154 | BackupObj = 0x13, 155 | AppObj = 0x14, 156 | AppVarObj = 0x15, 157 | TempProgObj = 0x16, 158 | GroupObj = 0x17, 159 | EquObj_2 = 0x23, 160 | }; 161 | 162 | enum TI86OBJ { 163 | RealObj86 = 0x00, 164 | CplxObj86 = 0x01, 165 | VectObj86 = 0x02, 166 | CVectObj86 = 0x03, 167 | ListObj86 = 0x04, 168 | CListObj86 = 0x05, 169 | MatObj86 = 0x06, 170 | CMatObj86 = 0x07, 171 | ConstObj86 = 0x08, 172 | CConst86 = 0x09, 173 | EquObj86 = 0x0A, 174 | StrngObj86 = 0x0C, 175 | FuncGDBObj86 = 0x0D, 176 | PolarGDBObj86 = 0x0E, 177 | ParamGDBObj86 = 0x0F, 178 | DiffEquGDBObj86 = 0x10, 179 | PictObj86 = 0x11, 180 | ProgObj86 = 0x12, 181 | DirObj86 = 0x15, 182 | FuncWSObj86 = 0x17, 183 | PolWSObj86 = 0x18, 184 | ParamWSObj86 = 0x19, 185 | DifEquWSObj86 = 0x1A, 186 | ZRCLObj86 = 0x1B, 187 | BackupObj86 = 0x1D, 188 | EquObj_286 = 0x2A, 189 | }; 190 | 191 | // used with linking 192 | #define FlashObj 0x24 193 | #define IDListObj 0x26 194 | #define EquObj_3 0x63 195 | 196 | LINK_ERR link_send_var(CPU_t *, TIFILE_t *, SEND_FLAG); 197 | LINK_ERR link_send_backup(CPU_t *, TIFILE_t *, SEND_FLAG); 198 | LINK_ERR forceload_os(CPU_t *, TIFILE_t *); 199 | int link_connect(CPU_t *, CPU_t *); 200 | int link_connect_hub(int slot, CPU_t *cpu); 201 | BOOL link_connected_hub(int slot); 202 | int link_disconnect(CPU_t *); 203 | void writeboot(FILE* , memory_context_t *, int page); 204 | #endif 205 | 206 | -------------------------------------------------------------------------------- /hardware/ti_stdint.h: -------------------------------------------------------------------------------- 1 | #ifndef STDINT_H 2 | #define STDINT_H 3 | 4 | #include "coretypes.h" 5 | 6 | typedef struct STDINT { 7 | unsigned char intactive; 8 | #ifdef NO_TIMER_ELAPSED 9 | uint64_t lastchk1; 10 | uint64_t timermax1; 11 | uint64_t lastchk2; 12 | uint64_t timermax2; 13 | uint64_t freq[4]; 14 | #else 15 | double lastchk1; 16 | double timermax1; 17 | double lastchk2; 18 | double timermax2; 19 | double freq[4]; 20 | #endif 21 | int mem; 22 | int xy; 23 | BOOL on_backup; 24 | BOOL on_latch; 25 | } STDINT_t; 26 | 27 | 28 | 29 | 30 | #endif 31 | -------------------------------------------------------------------------------- /interface/calc.h: -------------------------------------------------------------------------------- 1 | #ifndef _CALC_H 2 | #define _CALC_H 3 | 4 | #include "stdafx.h" 5 | #include "coretypes.h" 6 | 7 | #ifdef WXVER 8 | #include 9 | #endif 10 | #include "core.h" 11 | #include "lcd.h" 12 | #include "keys.h" 13 | #include "link.h" 14 | 15 | #ifdef _WINDOWS 16 | #include "Wabbitemu_h.h" 17 | #include "sound.h" 18 | #include "DropTarget.h" 19 | #include "dbbreakpoints.h" 20 | #endif 21 | 22 | #include "label.h" 23 | 24 | typedef enum { 25 | GDS_IDLE, 26 | GDS_STARTING, 27 | GDS_RECORDING, 28 | GDS_ENDING 29 | } gif_disp_states; 30 | 31 | #define MIN_BLOCK_SIZE 16 32 | #define MAX_FLASH_PAGE_SIZE 0x80 33 | #define MAX_RAM_PAGE_SIZE 0x08 34 | typedef struct profiler { 35 | BOOL running; 36 | int blockSize; 37 | long long totalTime; 38 | long flash_data[MAX_FLASH_PAGE_SIZE][PAGE_SIZE / MIN_BLOCK_SIZE]; 39 | long ram_data[MAX_RAM_PAGE_SIZE][PAGE_SIZE / MIN_BLOCK_SIZE]; 40 | } profiler_t; 41 | 42 | #define KEY_STRING_SIZE 56 43 | struct key_string { 44 | TCHAR *text; 45 | int group; 46 | int bit; 47 | int repeat; 48 | struct key_string *next; 49 | }; 50 | 51 | typedef struct tagCALC { 52 | #ifdef WINVER 53 | HWND (*breakpoint_callback)(struct tagCALC *); 54 | #elif MACVER 55 | void (*breakpoint_callback)(struct tagCALC *, void *); 56 | void *breakpoint_owner; 57 | #else 58 | void (*breakpoint_callback)(struct tagCALC *); 59 | #endif 60 | int slot; 61 | TCHAR rom_path[MAX_PATH]; 62 | char rom_version[32]; 63 | int model; 64 | 65 | time_t time_error; 66 | 67 | BOOL active; 68 | CPU_t cpu; 69 | memory_context_t mem_c; 70 | timer_context_t timer_c; 71 | #ifdef WINVER 72 | AUDIO_t *audio; // FIXME: Bad! 73 | #endif 74 | 75 | #ifdef WINVER 76 | CDropTarget *pDropTarget; 77 | HWND hwndFrame; 78 | HWND hwndLCD; 79 | HWND hwndDetachedFrame; 80 | HWND hwndDetachedLCD; 81 | HWND hwndStatusBar; 82 | HWND hwndDebug; 83 | HWND hwndSmallClose; 84 | HWND hwndSmallMinimize; 85 | HWND hwndKeyListDialog; 86 | HWND hwndTeacherView; 87 | HWND hwndTeacherViewScreen[3]; 88 | 89 | BOOL SkinEnabled; 90 | DWORD scale; 91 | BOOL bCutout; 92 | HANDLE hdlThread; 93 | 94 | clock_t sb_refresh; 95 | 96 | key_string *last_keypress_head; 97 | int num_keypresses; 98 | 99 | BOOL do_drag; 100 | HDC hdcSkin; 101 | HDC hdcButtons; 102 | HDC hdcKeymap; 103 | #elif WXVER 104 | wxImage calcSkin; 105 | wxImage keymap; 106 | int scale; 107 | bool SkinEnabled; 108 | bool bCutout; 109 | wxSize SkinSize; 110 | wxRect LCDRect; 111 | clock_t sb_refresh; 112 | bool bCustomSkin; 113 | char skin_path[256]; 114 | char keymap_path[256]; 115 | BOOL bTIOSDebug; 116 | #endif 117 | 118 | BOOL running; 119 | BOOL auto_turn_on; 120 | int speed; 121 | BYTE breakpoints[0x10000]; 122 | label_struct labels[6000]; 123 | profiler_t profiler; 124 | 125 | TCHAR labelfn[256]; 126 | applist_t applist; 127 | apphdr_t *last_transferred_app; 128 | 129 | gif_disp_states gif_disp_state; 130 | 131 | #ifdef WINVER 132 | RECT rectSkin; 133 | RECT rectLCD; 134 | COLORREF FaceplateColor; 135 | BOOL bCustomSkin; 136 | BOOL bAlwaysOnTop; 137 | BOOL bAlphaBlendLCD; 138 | BOOL bTIOSDebug; 139 | TCHAR skin_path[256]; 140 | TCHAR keymap_path[256]; 141 | IWabbitemu *pWabbitemu; 142 | ICalcNotify *pCalcNotify; 143 | #endif 144 | 145 | } calc_t; 146 | 147 | #ifdef WITH_BACKUPS 148 | typedef struct DEBUG_STATE { 149 | SAVESTATE_t *save; 150 | struct DEBUG_STATE *next, *prev; 151 | } debugger_backup; 152 | #endif 153 | 154 | #ifdef QUICKLOOK 155 | #define MAX_CALCS 1 156 | #else 157 | #define MAX_CALCS 8 158 | #endif 159 | #define MAX_SPEED 100*50 160 | 161 | typedef struct tagCALC CALC, *LPCALC; 162 | 163 | void calc_turn_on(LPCALC); 164 | LPCALC calc_slot_new(void); 165 | u_int calc_count(void); 166 | int calc_reset(LPCALC); 167 | int CPU_reset(CPU_t *); 168 | int calc_run_frame(LPCALC); 169 | int calc_run_seconds(LPCALC, double); 170 | int calc_run_timed(LPCALC, time_t); 171 | int calc_run_all(void); 172 | BOOL calc_start_screenshot(calc_t *calc, const char *filename); 173 | void calc_stop_screenshot(calc_t *calc); 174 | 175 | #ifdef WITH_BACKUPS 176 | void do_backup(LPCALC); 177 | void restore_backup(int index, LPCALC); 178 | void init_backups(); 179 | void free_backups(LPCALC); 180 | void free_backup(debugger_backup *); 181 | #endif 182 | 183 | BOOL rom_load(LPCALC lpCalc, LPCTSTR FileName); 184 | void calc_slot_free(LPCALC); 185 | 186 | void calc_unpause_linked(); 187 | void calc_pause_linked(); 188 | 189 | int calc_init_83p(LPCALC); 190 | int calc_init_84p(LPCALC); 191 | int calc_init_83pse(LPCALC); 192 | LPCALC calc_from_cpu(CPU_t *); 193 | LPCALC calc_from_memc(memc *); 194 | void calc_erase_certificate(unsigned char *, int); 195 | void port_debug_callback(void *, void *); 196 | void mem_debug_callback(void *); 197 | 198 | #ifdef CALC_C 199 | #define GLOBAL 200 | #else 201 | #define GLOBAL extern 202 | #endif 203 | 204 | GLOBAL calc_t calcs[MAX_CALCS]; 205 | //GLOBAL LPCALC lpDebuggerCalc; 206 | 207 | #ifdef WITH_BACKUPS 208 | #define MAX_BACKUPS 10 209 | GLOBAL debugger_backup * backups[MAX_CALCS]; 210 | GLOBAL int number_backup; 211 | GLOBAL int current_backup_index; 212 | GLOBAL int num_backup_per_sec; 213 | #endif 214 | 215 | #ifdef WITH_AVI 216 | #include "avi_utils.h" 217 | #include "avifile.h" 218 | GLOBAL CAviFile *currentAvi; 219 | GLOBAL HAVI recording_avi; 220 | GLOBAL BOOL is_recording; 221 | #endif 222 | 223 | GLOBAL u_int frame_counter; 224 | GLOBAL int startX; 225 | GLOBAL int startY; 226 | GLOBAL BOOL exit_save_state; 227 | GLOBAL BOOL check_updates; 228 | GLOBAL BOOL new_calc_on_load_files; 229 | GLOBAL BOOL do_backups; 230 | GLOBAL BOOL break_on_exe_violation; 231 | GLOBAL BOOL break_on_invalid_flash; 232 | GLOBAL BOOL sync_cores; 233 | GLOBAL link_t *link_hub[MAX_CALCS + 1]; 234 | GLOBAL int link_hub_count; 235 | GLOBAL int calc_waiting_link; 236 | 237 | GLOBAL const TCHAR *CalcModelTxt[] 238 | #ifdef CALC_C 239 | = { //"???", 240 | _T("TI-81"), 241 | _T("TI-82"), 242 | _T("TI-83"), 243 | _T("TI-85"), 244 | _T("TI-86"), 245 | _T("TI-73"), 246 | _T("TI-83+"), 247 | _T("TI-83+SE"), 248 | _T("TI-84+"), 249 | _T("TI-84+SE"), 250 | _T("???")} 251 | #endif 252 | ; 253 | 254 | #define _HAS_CALC_H 255 | #endif 256 | -------------------------------------------------------------------------------- /interface/state.h: -------------------------------------------------------------------------------- 1 | #ifndef STATE_H_ 2 | #define STATE_H_ 3 | 4 | #include "core.h" 5 | #include "var.h" // TIFILE 6 | 7 | typedef struct apphdr { 8 | TCHAR name[12]; 9 | u_int page, page_count; 10 | } apphdr_t; 11 | 12 | typedef struct applist { 13 | u_int count; 14 | apphdr_t apps[96]; 15 | } applist_t; 16 | 17 | typedef struct { 18 | uint8_t type_ID; 19 | uint8_t type_ID2; 20 | uint8_t version; 21 | uint16_t address; 22 | uint8_t page; 23 | uint8_t name_len; 24 | uint8_t length; 25 | TCHAR name[9]; 26 | } symbol83P_t; 27 | 28 | typedef struct symlist { 29 | symbol83P_t *programs; 30 | symbol83P_t *last; 31 | symbol83P_t symbols[512]; 32 | } symlist_t; 33 | 34 | //83p 35 | #define pTemp 0x982E 36 | #define progPtr 0x9830 37 | #define symTable 0xFE66 38 | //86 39 | #define VAT_END_86 0xD298 40 | 41 | typedef struct upages { 42 | u_int start, end; 43 | } upages_t; 44 | 45 | #define circ10(z) ((((u_char) z) < 10) ? ((z) + 1) % 10 : (z)) 46 | #define tAns 0x72 47 | 48 | void state_build_applist(CPU_t *, applist_t *); 49 | void state_userpages(CPU_t *, upages_t *); 50 | symlist_t *state_build_symlist_86(CPU_t *, symlist_t *); 51 | symlist_t *state_build_symlist_83P(CPU_t *, symlist_t *); 52 | TCHAR *GetRealAns(CPU_t*); 53 | TCHAR *Symbol_Name_to_String(int model, symbol83P_t *, TCHAR *); 54 | TCHAR *App_Name_to_String(apphdr_t *, TCHAR *); 55 | 56 | #endif /*STATE_H_*/ 57 | -------------------------------------------------------------------------------- /makefile.old: -------------------------------------------------------------------------------- 1 | .SUFFIXES: 2 | .SUFFIXES: .o .c 3 | 4 | WXVERSION=2.8 5 | CFLAGS=-I. -I./core -I./debugger -I./gui -I./hardware -I./interface -I./utilities -x c++ -ggdb -c\ 6 | -DHIGH_SHADE_GIF -DVERBOSE -D_LINUX -DWXVER `wx-config --version=$(WXVERSION) --unicode=yes --cflags` -Wall 7 | CXXFLAGS=-I. -I./core -I./debugger -I./gui -I./hardware -I./interface -I./utilities -x c++ -ggdb -c\ 8 | -DHIGH_SHADE_GIF -DVERBOSE -D_LINUX -DWXVER `wx-config --version=$(WXVERSION) --unicode=yes --cppflags` -Wall 9 | LDFLAGS=`wx-config --version=$(WXVERSION) --unicode=yes --libs` -lstdc++ 10 | CC=gcc 11 | CXX=g++ 12 | LD=g++ 13 | PROGRAM=wxwabbitemu 14 | 15 | .SUFFIXES: .o .cpp .c 16 | .c.o: 17 | $(CC) -c $(CFLAGS) $*.c 18 | .cpp.o: 19 | $(CXX) -c $(CXXFLAGS) $*.c 20 | 21 | all: directory wabbitemu 22 | 23 | directory: 24 | mkdir -p ./obj 25 | 26 | # Apparently some versions of GCC (like 4.7.020120324) don't like the order 27 | # $(LD) $(LDFLAGS) *.o -o $(PROGRAM), and will want to commit suicide instead. 28 | # This fixes this issue. 29 | wabbitemu: core.o alu.o control.o device.o indexcb.o calc.o state.o gif.o\ 30 | gifhandle.o label.o savestate.o sendfile.o var.o 81hw.o 83hw.o\ 31 | 83phw.o 83psehw.o 86hw.o keys.o lcd.o link.o gui.o guilcd.o\ 32 | droptarget.o guidebug.o disassemblyview.o disassemble.o romwizard.o\ 33 | wizardstart.o wizardcalctype.o wizardos.o fileutilities.o exportvar.o\ 34 | regpane.o flagspane.o guivartree.o cpupane.o guiskinwindow.o guiapp.o 35 | $(LD) *.o $(LDFLAGS) -o $(PROGRAM) 36 | 37 | core.o: ./core/core.c 38 | $(CXX) $(CXXFLAGS) ./core/core.c 39 | 40 | alu.o: ./core/alu.c 41 | $(CXX) $(CXXFLAGS) ./core/alu.c 42 | 43 | device.o: ./core/device.c 44 | $(CXX) $(CXXFLAGS) ./core/device.c 45 | 46 | control.o: ./core/control.c 47 | $(CXX) $(CXXFLAGS) ./core/control.c 48 | 49 | indexcb.o: ./core/indexcb.c 50 | $(CXX) $(CXXFLAGS) ./core/indexcb.c 51 | 52 | calc.o: ./interface/calc.c 53 | $(CXX) $(CXXFLAGS) ./interface/calc.c 54 | 55 | state.o: ./interface/state.c 56 | $(CXX) $(CXXFLAGS) ./interface/state.c 57 | 58 | exportvar.o: ./utilities/exportvar.c 59 | $(CXX) $(CXXFLAGS) ./utilities/exportvar.c 60 | 61 | fileutilities.o: ./utilities/fileutilities.c 62 | $(CXX) $(CXXFLAGS) ./utilities/fileutilities.c 63 | 64 | gif.o: ./utilities/gif.c 65 | $(CXX) $(CXXFLAGS) ./utilities/gif.c 66 | 67 | gifhandle.o: ./utilities/gifhandle.c 68 | $(CXX) $(CXXFLAGS) ./utilities/gifhandle.c 69 | 70 | label.o: ./utilities/label.c 71 | $(CXX) $(CXXFLAGS) ./utilities/label.c 72 | 73 | savestate.o: ./utilities/savestate.c 74 | $(CXX) $(CXXFLAGS) ./utilities/savestate.c 75 | 76 | var.o: ./utilities/var.c 77 | $(CXX) $(CXXFLAGS) ./utilities/var.c 78 | 79 | sendfile.o: ./utilities/sendfile.c 80 | $(CXX) $(CXXFLAGS) ./utilities/sendfile.c 81 | 82 | 81hw.o: ./hardware/81hw.c 83 | $(CXX) $(CXXFLAGS) ./hardware/81hw.c 84 | 85 | 83hw.o: ./hardware/83hw.c 86 | $(CXX) $(CXXFLAGS) ./hardware/83hw.c 87 | 88 | 83phw.o: ./hardware/83phw.c 89 | $(CXX) $(CXXFLAGS) ./hardware/83phw.c 90 | 91 | 83psehw.o: ./hardware/83psehw.c 92 | $(CXX) $(CXXFLAGS) ./hardware/83psehw.c 93 | 94 | 86hw.o: ./hardware/86hw.c 95 | $(CXX) $(CXXFLAGS) ./hardware/86hw.c 96 | 97 | keys.o: ./hardware/keys.c 98 | $(CXX) $(CXXFLAGS) ./hardware/keys.c 99 | 100 | lcd.o: ./hardware/lcd.c 101 | $(CXX) $(CXXFLAGS) ./hardware/lcd.c 102 | 103 | link.o: ./hardware/link.c 104 | $(CXX) $(CXXFLAGS) ./hardware/link.c 105 | 106 | gui.o: ./gui/gui.cpp ./gui/gui.h 107 | $(CXX) $(CXXFLAGS) ./gui/gui.cpp 108 | 109 | guiapp.o: ./gui/guiapp.cpp ./gui/guiapp.h 110 | $(CXX) $(CXXFLAGS) ./gui/guiapp.cpp 111 | 112 | guiskinwindow.o: ./gui/guiskinwindow.cpp ./gui/guiskinwindow.h 113 | $(CXX) $(CXXFLAGS) ./gui/guiskinwindow.cpp 114 | 115 | guilcd.o: ./gui/guilcd.cpp ./gui/guilcd.h 116 | $(CXX) $(CXXFLAGS) ./gui/guilcd.cpp 117 | 118 | guivartree.o: ./gui/guivartree.cpp ./gui/guivartree.h 119 | $(CXX) $(CXXFLAGS) ./gui/guivartree.cpp 120 | 121 | droptarget.o: ./gui/droptarget.cpp ./gui/droptarget.h 122 | $(CXX) $(CXXFLAGS) ./gui/droptarget.cpp 123 | 124 | wizardstart.o: ./gui/wizard/wizardstart.cpp ./gui/wizard/wizardstart.h 125 | $(CXX) $(CXXFLAGS) ./gui/wizard/wizardstart.cpp 126 | 127 | wizardcalctype.o: ./gui/wizard/wizardcalctype.cpp ./gui/wizard/wizardcalctype.h 128 | $(CXX) $(CXXFLAGS) ./gui/wizard/wizardcalctype.cpp 129 | 130 | wizardos.o: ./gui/wizard/wizardos.cpp ./gui/wizard/wizardos.h 131 | $(CXX) $(CXXFLAGS) ./gui/wizard/wizardos.cpp 132 | 133 | romwizard.o: ./gui/wizard/romwizard.cpp ./gui/wizard/romwizard.h 134 | $(CXX) $(CXXFLAGS) ./gui/wizard/romwizard.cpp 135 | 136 | guidebug.o: ./debugger/guidebug.cpp ./debugger/guidebug.h 137 | $(CXX) $(CXXFLAGS) ./debugger/guidebug.cpp 138 | 139 | disassemblyview.o: ./debugger/disassemblyview.cpp ./debugger/disassemblyview.h 140 | $(CXX) $(CXXFLAGS) ./debugger/disassemblyview.cpp 141 | 142 | disassemble.o: ./debugger/disassemble.c 143 | $(CXX) $(CXXFLAGS) ./debugger/disassemble.c 144 | 145 | regpane.o: ./debugger/panes/regpane.cpp ./debugger/panes/regpane.h 146 | $(CXX) $(CXXFLAGS) ./debugger/panes/regpane.cpp 147 | 148 | flagspane.o: ./debugger/panes/flagspane.cpp ./debugger/panes/flagspane.h 149 | $(CXX) $(CXXFLAGS) ./debugger/panes/flagspane.cpp 150 | 151 | cpupane.o: ./debugger/panes/cpupane.cpp ./debugger/panes/cpupane.h 152 | $(CXX) $(CXXFLAGS) ./debugger/panes/cpupane.cpp 153 | 154 | clean : 155 | rm -f *.o $(PROGRAM) 156 | -------------------------------------------------------------------------------- /meson.build: -------------------------------------------------------------------------------- 1 | # Portions of this come from KiCad's CMakeLists.txt 2 | # set the project name 3 | project('wxWabbitemu', ['c', 'cpp'], 4 | version: '0.1.0', 5 | license: 'GPL2+', 6 | default_options : ['default_library=static']) 7 | 8 | # find wx + include it 9 | # Turn on wxWidgets compatibility mode for some classes 10 | add_global_arguments('-DWX_COMPATIBILITY', language: ['c', 'cpp']) 11 | 12 | # wxWabbitemu specific defines 13 | add_global_arguments('-DHIGH_SHADE_GIF', '-DVERBOSE', '-D_LINUX', '-DWXVER', language: ['c', 'cpp']) 14 | 15 | # Enable Unicode, as needed 16 | compiler = meson.get_compiler('cpp') 17 | 18 | if ['gcc', 'clang'].contains(compiler.get_id()) 19 | if compiler.version().version_compare('>=4.8.0') 20 | add_global_arguments('-D_UNICODE', language: ['c', 'cpp']) 21 | endif 22 | endif 23 | 24 | # now hunt for wxWidgets 25 | # (adv is used for "advanced" widgets, such as the wizard) 26 | wxWidgets_dep = dependency('wxWidgets', required: true, modules: ['adv', 'net', 'core', 'base'], static: false) 27 | 28 | # includes 29 | includes = include_directories( 30 | 'core', 31 | 'debugger', 32 | 'gui', 33 | 'hardware', 34 | 'interface', 35 | 'utilities' 36 | ) 37 | 38 | # add the executable 39 | wxWabbitemu_exe = executable('wxWabbitemu', 40 | # Core 41 | 'core/core.c', 42 | 'core/alu.c', 43 | 'core/control.c', 44 | 'core/device.c', 45 | 'core/indexcb.c', 46 | 47 | # Calc Interfacing 48 | 'interface/calc.c', 49 | 'interface/state.c', 50 | 51 | # Utilities/Libraries 52 | 'utilities/exportvar.c', 53 | 'utilities/fileutilities.c', 54 | 'utilities/gif.c', 55 | 'utilities/gifhandle.c', 56 | 'utilities/label.c', 57 | 'utilities/savestate.c', 58 | 'utilities/sendfile.c', 59 | 'utilities/var.c', 60 | 61 | # Hardware Emulation 62 | 'hardware/81hw.c', 63 | 'hardware/83hw.c', 64 | 'hardware/83phw.c', 65 | 'hardware/83psehw.c', 66 | 'hardware/86hw.c', 67 | 'hardware/keys.c', 68 | 'hardware/lcd.c', 69 | 'hardware/link.c', 70 | 71 | # wxWidgets GUI 72 | 'gui/gui.cpp', # This requires ../gui/gui.h 73 | 'gui/guiapp.cpp', # This requires ../gui/guiapp.h 74 | 'gui/guiskinwindow.cpp', # This requires ../gui/guiskinwindow.h 75 | 'gui/guilcd.cpp', # This requires ../gui/guilcd.h 76 | 'gui/guivartree.cpp', # This requires ../gui/guivartree.h 77 | 'gui/droptarget.cpp', # This requires ../gui/droptarget.h 78 | 'gui/wizard/wizardstart.cpp', # This requires ../gui/wizard/wizardstart.h 79 | 'gui/wizard/wizardcalctype.cpp', # This requires ../gui/wizard/wizardcalctype.h 80 | 'gui/wizard/wizardos.cpp', # This requires ../gui/wizard/wizardos.h 81 | 'gui/wizard/romwizard.cpp', # This requires ../gui/wizard/romwizard.h 82 | 'debugger/guidebug.cpp', # This requires ../debugger/guidebug.h 83 | 84 | # Debugger and debugger GUI 85 | 'debugger/disassemblyview.cpp', # This requires ../debugger/disassemblyview.h 86 | 'debugger/disassemble.c', 87 | 'debugger/panes/regpane.cpp', # This requires ../debugger/panes/regpane.h 88 | 'debugger/panes/flagspane.cpp', # This requires ../debugger/panes/flagspane.h 89 | 'debugger/panes/cpupane.cpp', # This requires ../debugger/panes/cpupane.h 90 | 91 | dependencies: wxWidgets_dep, 92 | 93 | # mixing of C and C++ necessitates builds in c++ 94 | c_args: ['-x', 'c++'], 95 | 96 | include_directories: includes, 97 | install: true 98 | ) 99 | 100 | -------------------------------------------------------------------------------- /premake/Makefile: -------------------------------------------------------------------------------- 1 | MAKEFILES = ../build/Makefile ../build/wxWabbitemu.make 2 | 3 | all: $(MAKEFILES) 4 | 5 | $(MAKEFILES): 6 | ./create_makefile.sh 7 | 8 | distclean: 9 | rm -f $(MAKEFILES) 10 | -------------------------------------------------------------------------------- /premake/create_makefile.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" 3 | 4 | ######################## 5 | # Change directory 6 | ######################## 7 | cd "$SCRIPT_DIR" 8 | 9 | ######################## 10 | # Create Makefiles 11 | ######################## 12 | echo " ** Creating Makefiles..." 13 | ./premake4 gmake 14 | 15 | ######################## 16 | # Add wxWidgetsVer.make 17 | ######################## 18 | echo " ** Adding dynamic wxWidgets version detection..." 19 | echo "# NOTE - this file has been modified to allow building with 2.8 and 3.0 20 | # Regenerating the Makefile will overwrite this change! 21 | 22 | include wxWidgetsVer.make 23 | 24 | # End patch by patch_makefile.sh (patched on `date`) 25 | " | cat - ../build/wxWabbitemu.make > wxWabbitemu.make.changed && mv wxWabbitemu.make.changed ../build/wxWabbitemu.make 26 | 27 | ######################## 28 | # Use wxWidgetsVer vars 29 | ######################## 30 | echo " ** Configuring Makefile to use dynamic wxWidgets versioning..." 31 | perl -pi -e 's|`wx-config .*?--cxxflags.*?`|\$\(WX_CFLAGS\)|g' ../build/wxWabbitemu.make 32 | perl -pi -e 's|`wx-config .*?--libs.*?`|\$\(WX_LDFLAGS\)|g' ../build/wxWabbitemu.make 33 | 34 | echo " ** Done!" 35 | -------------------------------------------------------------------------------- /premake/premake4: -------------------------------------------------------------------------------- 1 | premake4_linux_x86 -------------------------------------------------------------------------------- /premake/premake4.lua: -------------------------------------------------------------------------------- 1 | dofile "use_wxwidgets.lua" 2 | solution "wxWabbitemu" 3 | configurations {"Debug", "Release"} 4 | location "../build" -- optional, but cleaner 5 | targetdir "../bin" -- optional, same here 6 | 7 | configuration "Debug" 8 | defines { "DEBUG" } 9 | flags { "Symbols", "ExtraWarnings" } 10 | configuration "Release" 11 | flags { "Optimize" } 12 | 13 | configuration { "linux", "gmake" } 14 | buildoptions { "-x c++" } 15 | 16 | project "wxWabbitemu" 17 | kind "WindowedApp" 18 | language "C++" 19 | wx_config {Unicode="yes", Version="2.8"} 20 | includedirs { 21 | "..", 22 | "../core", 23 | "../debugger", 24 | "../gui", 25 | "../hardware", 26 | "../interface", 27 | "../utilities" 28 | } 29 | defines { 30 | "HIGH_SHADE_GIF", 31 | "VERBOSE", 32 | "_LINUX", 33 | "WXVER" 34 | } 35 | files { 36 | -- Core 37 | "../core/core.c", 38 | "../core/alu.c", 39 | "../core/control.c", 40 | "../core/device.c", 41 | "../core/indexcb.c", 42 | -- Calc Interfacing 43 | "../interface/calc.c", 44 | "../interface/state.c", 45 | -- Utilities/Libraries 46 | "../utilities/exportvar.c", 47 | "../utilities/fileutilities.c", 48 | "../utilities/gif.c", 49 | "../utilities/gifhandle.c", 50 | "../utilities/label.c", 51 | "../utilities/savestate.c", 52 | "../utilities/sendfile.c", 53 | "../utilities/var.c", 54 | -- Hardware Emulation 55 | "../hardware/81hw.c", 56 | "../hardware/83hw.c", 57 | "../hardware/83phw.c", 58 | "../hardware/83psehw.c", 59 | "../hardware/86hw.c", 60 | "../hardware/keys.c", 61 | "../hardware/lcd.c", 62 | "../hardware/link.c", 63 | -- wxWidgets GUI 64 | "../gui/gui.cpp", -- This requires ../gui/gui.h 65 | "../gui/guiapp.cpp", -- This requires ../gui/guiapp.h 66 | "../gui/guiskinwindow.cpp", -- This requires ../gui/guiskinwindow.h 67 | "../gui/guilcd.cpp", -- This requires ../gui/guilcd.h 68 | "../gui/guivartree.cpp", -- This requires ../gui/guivartree.h 69 | "../gui/droptarget.cpp", -- This requires ../gui/droptarget.h 70 | "../gui/wizard/wizardstart.cpp", -- This requires ../gui/wizard/wizardstart.h 71 | "../gui/wizard/wizardcalctype.cpp", -- This requires ../gui/wizard/wizardcalctype.h 72 | "../gui/wizard/wizardos.cpp", -- This requires ../gui/wizard/wizardos.h 73 | "../gui/wizard/romwizard.cpp", -- This requires ../gui/wizard/romwizard.h 74 | "../debugger/guidebug.cpp", -- This requires ../debugger/guidebug.h 75 | -- Debugger and debugger GUI 76 | "../debugger/disassemblyview.cpp", -- This requires ../debugger/disassemblyview.h 77 | "../debugger/disassemble.c", 78 | "../debugger/panes/regpane.cpp", -- This requires ../debugger/panes/regpane.h 79 | "../debugger/panes/flagspane.cpp", -- This requires ../debugger/panes/flagspane.h 80 | "../debugger/panes/cpupane.cpp" -- This requires ../debugger/panes/cpupane.h 81 | } 82 | 83 | newaction { 84 | trigger = "install", 85 | description = "Install wxWabbitemu", 86 | execute = function () 87 | os.copyfile("bin/wxwabbitemu", "/usr/bin/wxwabbitemu") 88 | end 89 | } 90 | -------------------------------------------------------------------------------- /premake/premake4_linux_x86: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/premake/premake4_linux_x86 -------------------------------------------------------------------------------- /premake/use_wxwidgets.lua: -------------------------------------------------------------------------------- 1 | -- use_wxwidgets.lua 2 | -- wxWidgets configuration file for premake4 3 | -- 4 | -- authors: laurent.humbertclaude@gmail.com 5 | -- v.krishnakumar@gmail.com 6 | 7 | -- optional root folder of wxwidgets installation folder 8 | -- 9 | newoption { 10 | trigger = "wx_root", 11 | value = "PATH", 12 | description = "Path to wxwidgets root folder, by default, WXWIN envvar will be used or wx-config found in path on POSIX" 13 | } 14 | 15 | -- The wx_config the parameters are. 16 | -- Root : path to wx root folder. Can be left empty if WXWIN is defined 17 | -- or if wx-config is accessible. 18 | -- Debug : "yes" use debug version of wxwidgets. Default to "no" 19 | -- Version : one of '2.4', '2.5', '2.6', '2.7', '2.8', '2.9', '3.0'. Default to '3.0' 20 | -- Static : indicates how wx is to be linked. Values are 21 | -- either "yes" for static linking or "no" for shared linking, Default to "no" 22 | -- Unicode : use "yes" for unicode or "no" for ansi version. 23 | -- ansi version only available up to 2.8 24 | -- Default to "yes" 25 | -- Universal : use universal configuration. Default to "no" 26 | -- Libs : a list of wx libraries that you want to link with. 27 | -- eg: "aui,media,html" 28 | -- Default to "richtext,aui,xrc,qa,html,adv,core,xml,net"; base is implicit 29 | -- WindowsCompiler : compiler used to compile windows libraries ( "vc" or "gcc" ) 30 | 31 | function wx_config(options) 32 | 33 | local wrongParam = false 34 | local allowedWxOptions = {"Root", "Debug", "Host", "Version", "Static", "Unicode", "Universal", "Libs", "WindowsCompiler" } 35 | for option in pairs(options) do 36 | if not table.contains(allowedWxOptions, option) then 37 | print ("unrecognized option '"..option.. "'") 38 | wrongParam = true 39 | end 40 | end 41 | if wrongParam then print("valid options are : '" .. table.concat(allowedWxOptions, "', '").."'") end 42 | 43 | wx_config_Private( options.Root or "", 44 | options.Debug or "", 45 | options.Host or "", 46 | options.Version or "3.0", 47 | options.Static or "", 48 | options.Unicode or "yes", 49 | options.Universal or "", 50 | options.Libs or "richtext,aui,xrc,qa,html,adv,core,xml,net", -- base is implicit, std not valid 51 | options.WindowsCompiler or "vc" 52 | ) 53 | end 54 | 55 | function wx_config_Private(wxRoot, wxDebug, wxHost, wxVersion, wxStatic, wxUnicode, wxUniversal, wxLibs, wxWindowsCompiler) 56 | -- some options are not allowed for newer version of wxWidgets 57 | if wxVersion > "2.8" then -- alphabetical comparison may fail... 58 | -- wxDebug = "" -- 3.0 still make debug libraries 59 | wxUnicode = "yes" 60 | end 61 | 62 | --wx_root=PATH override wxRoot parameter 63 | if _OPTIONS and _OPTIONS["wx_root"] then 64 | print ("seen option '--wx_root=" .. _OPTIONS["wx_root"] .. "' overriding default root = '" .. wxRoot .. "'") 65 | wxRoot = _OPTIONS["wx_root"] 66 | end 67 | -- the environment variable WXWIN override both wxRoot parameter and --wx_root option 68 | if os.getenv('WXWIN') then wxRoot = os.getenv('WXWIN') end 69 | 70 | if wxUnicode == "yes" then defines { "_UNICODE" } end 71 | 72 | if wxDebug == "yes" then defines { "__WXDEBUG__" } 73 | elseif wxDebug == "no" then flags { "Optimize" } end 74 | 75 | if wxStatic == "yes" then 76 | flags { "StaticRuntime" } 77 | else 78 | defines { "WXUSINGDLL" } 79 | end 80 | 81 | 82 | -- function to compensate lack of wx-config program on windows 83 | -- but wait, look at http://sites.google.com/site/wxconfig/ for one ! 84 | function wx_config_for_windows(wxWindowsCompiler) 85 | local wxBuildType = "" -- buildtype is one of "", "u", "d" or "ud" 86 | local wxDebugSuffix = "" -- debug buildsuffix is for support libraries only 87 | if wxUnicode ~= "" then wxBuildType = wxBuildType .. "u" end 88 | if wxDebug == "yes" then 89 | wxBuildType = wxBuildType .. "d" 90 | wxDebugSuffix = "d" 91 | end 92 | 93 | local wxLibPath = path.join(wxRoot, "lib") 94 | wxLibPath = path.join(wxLibPath, wxWindowsCompiler .. "_" .. iif(wxStatic == 'yes', 'lib', 'dll')) 95 | -- common defines 96 | defines{ "__WXMSW__" } 97 | 98 | -- common include path 99 | includedirs { 100 | path.join(wxRoot, "include"), 101 | path.join(wxLibPath, "msw" .. wxBuildType) -- something like "%WXWIN%\lib\vc_lib\mswud" to find "wx/setup.h" 102 | } 103 | 104 | -- common library path 105 | libdirs { wxLibPath } 106 | 107 | -- add the libs 108 | libVersion = string.gsub(wxVersion, '%.', '') -- remove dot from version 109 | links { "wxbase"..libVersion..wxBuildType } -- base lib 110 | for i, lib in ipairs(string.explode(wxLibs, ",")) do 111 | local libPrefix = 'wxmsw' 112 | if lib == "xml" or lib == "net" or lib == "odbc" then 113 | libPrefix = 'wxbase' 114 | end 115 | links { libPrefix..libVersion..wxBuildType..'_'..lib} 116 | end 117 | -- link with support libraries 118 | for i, lib in ipairs({"wxjpeg", "wxpng", "wxzlib", "wxtiff", "wxexpat"}) do 119 | links { lib..wxDebugSuffix } 120 | end 121 | links { "wxregex" .. wxBuildType } 122 | end 123 | 124 | -- use wx-config to figure out build parameters 125 | function wx_config_for_posix() 126 | local configCmd = "wx-config" -- this is the wx-config command ligne 127 | if wxRoot ~= "" then configCmd = path.join(wxRoot, "bin/wx-config") end 128 | 129 | local function checkYesNo(value, option) 130 | if value == "" then return "" end 131 | if value == "yes" or value == "no" then return " --"..option.."="..value end 132 | error("wx"..option..' can only be "yes", "no" or empty' ) 133 | end 134 | 135 | configCmd = configCmd .. checkYesNo(wxDebug, "debug") 136 | configCmd = configCmd .. checkYesNo(wxStatic, "static") 137 | configCmd = configCmd .. checkYesNo(wxUnicode, "unicode") 138 | configCmd = configCmd .. checkYesNo(wxUniversal, "universal") 139 | if wxHost ~= "" then configCmd = configCmd .. " --host=" .. wxHost end 140 | if wxVersion ~= "" then configCmd = configCmd .. " --version=" .. wxVersion end 141 | 142 | -- set the parameters to the curent configuration 143 | buildoptions{"`" .. configCmd .." --cxxflags`"} 144 | linkoptions{"`" .. configCmd .." --libs " .. wxLibs .. "`"} 145 | end 146 | 147 | -- BUG: here, using any configuration() function will reset the current filter 148 | -- and apply configuration to all project configuration... 149 | -- see http://industriousone.com/post/add-way-refine-configuration-filter 150 | -- and http://sourceforge.net/tracker/?func=detail&aid=2936443&group_id=71616&atid=531881 151 | --~ configuration "not windows" 152 | --~ wx_config_for_posix() 153 | --~ configuration "vs*" 154 | --~ wx_config_for_windows("vc") 155 | --~ configuration {"windows", "codeblocks or gmake or codelitle"} 156 | --~ wx_config_for_windows("gcc") 157 | if os.get() ~= "windows" then 158 | wx_config_for_posix() 159 | else 160 | local allowedCompiler = {"vc", "gcc"} 161 | if not table.contains( allowedCompiler, wxWindowsCompiler) then 162 | print( "wrong wxWidgets Compiler specified('"..wxWindowsCompiler.."'), should be one of '".. table.concat(allowedCompiler, "', '").."'" ) 163 | wxWindowsCompiler = "vc" 164 | end 165 | --~ BUG/WISH: I need a function like compiler.get() that return the project/configuration compiler 166 | --~ local wxWindowsCompiler = "vc" 167 | --~ BUG? --cc=compiler standard premake option is not registered in the _OPTIONS array 168 | --~ if _OPTIONS and _OPTIONS["cc"] then 169 | --~ wxWindowsCompiler = _OPTIONS.cc 170 | --~ print("seen option '--cc=" .. _OPTIONS["cc"] .. "' overriding default cc='vc'") 171 | --~ end 172 | wx_config_for_windows(wxWindowsCompiler) 173 | end 174 | end 175 | 176 | -------------------------------------------------------------------------------- /res/break.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/break.bmp -------------------------------------------------------------------------------- /res/goto.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/goto.bmp -------------------------------------------------------------------------------- /res/membreak.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/membreak.bmp -------------------------------------------------------------------------------- /res/run.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/run.bmp -------------------------------------------------------------------------------- /res/step.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/step.bmp -------------------------------------------------------------------------------- /res/stepover.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/stepover.bmp -------------------------------------------------------------------------------- /res/stop.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/stop.bmp -------------------------------------------------------------------------------- /res/ti-icons.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/res/ti-icons.png -------------------------------------------------------------------------------- /stdafx.h: -------------------------------------------------------------------------------- 1 | #ifndef _STDAFX_H 2 | #define _STDAFX_H 3 | 4 | #if defined(_WINDOWS) 5 | #pragma once 6 | 7 | #define _WIN32_LEAN_AND_MEAN 8 | 9 | #ifndef STRICT 10 | #define STRICT 11 | #endif 12 | 13 | #define _ATL_NO_AUTOMATIC_NAMESPACE 14 | #define _ATL_CSTRING_EXPLICIT_CONSTRUCTORS // some CString constructors will be explicit 15 | 16 | #include 17 | #include 18 | #include 19 | #include 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | #define _CRTDBG_MAP_ALLOC 32 | #include 33 | #include 34 | 35 | #include 36 | #include 37 | #include 38 | #include 39 | #include 40 | 41 | 42 | #ifdef __cplusplus 43 | #include 44 | using namespace Gdiplus; 45 | #include 46 | #include 47 | #include 48 | using namespace ATL; 49 | #include 50 | #include 51 | #include 52 | #include 53 | 54 | namespace std 55 | { 56 | #ifdef UNICODE 57 | typedef std::wstring tstring; 58 | #else 59 | typedef std::string tstring; 60 | #endif 61 | } 62 | #endif 63 | 64 | #elif defined(_LINUX) 65 | #include 66 | #include 67 | #include 68 | #include 69 | #include 70 | #include 71 | #include 72 | #include 73 | #include 74 | #ifdef _UNICODE 75 | #include 76 | #endif 77 | #ifdef WXVER 78 | #include 79 | #undef _T 80 | #endif 81 | 82 | typedef void *LPVOID; 83 | #define MAX_PATH 256 84 | #ifndef _T 85 | #ifdef _UNICODE 86 | #define _T(z) L ## z 87 | #define TCHAR wchar_t 88 | typedef const wchar_t *LPCTSTR; 89 | typedef wchar_t *LPTSTR; 90 | 91 | #define _tcscpy _tcscpy_s 92 | #define _tcscpy_s std::wcscpy 93 | #define _tcsncpy std::wcsncpy 94 | //TODO: fix this to actually properly pass the size 95 | #define _tprintf_s(buffer, format, ...) swprintf(buffer, MAX_PATH, format, __VA_ARGS__) 96 | #define _tprintf _tprintf_s 97 | #define _tcsicmp wcscasecmp 98 | #define _tcscmp wcscmp 99 | #define _tcsncmp wcsncmp 100 | #define _putts puts 101 | #define _tcsrchr wcsrchr 102 | #define _tcslen wcslen 103 | #define _tfopen_s(file, mode) fopen(wxFNCONV(file), (char *)mode) 104 | #define _stscanf swscanf 105 | #define _tcscat wcscat 106 | #define _vstprintf(buffer, format, ...) vswprintf(buffer, wcslen(buffer), format, __VA_ARGS__) 107 | #define _vftprintf vfwprintf 108 | #define _tcsnicmp wcsncasecmp 109 | #else 110 | #define _T(z) z 111 | #define TCHAR char 112 | typedef const char *LPCTSTR; 113 | typedef char *LPCTSTR; 114 | 115 | #define _tprintf_s _tprintf 116 | #define _tprintf sprintf 117 | #define _tcsicmp strcasecmp 118 | #define _putts puts 119 | #define _tcsrchr strrchr 120 | #define _tcsncpy strncpy 121 | #define _tcscpy_s strcpy 122 | #define _tcscpy strcpy 123 | #define _tcslen strlen 124 | #define _tcsncmp strncmp 125 | #define _tcscmp strcmp 126 | #define _tfopen_s fopen 127 | #define _stscanf sscanf 128 | #define _tcscat strcat 129 | #define _vftprintf vfprintf 130 | #define _vstprintf vsprintf 131 | #define _tcsnicmp strncasecmp 132 | #endif 133 | #endif 134 | #define _strnicmp strncasecmp 135 | #define ARRAYSIZE(z) (sizeof(z)/sizeof((z)[0])) 136 | #define ZeroMemory(dest, size) memset(dest, 0, size) 137 | 138 | #elif defined(_MACVER) 139 | #include 140 | #include 141 | #include 142 | #include 143 | #include 144 | #include 145 | #include 146 | #include 147 | #include 148 | #include 149 | 150 | /* 151 | typedef char TCHAR; 152 | typedef void *LPVOID; 153 | typedef const char *LPCTSTR; 154 | typedef u_int8_t uint8_t; 155 | typedef u_int16_t uint16_t; 156 | typedef u_int32_t uint32_t; 157 | typedef u_int8_t BYTE, *LPBYTE; 158 | typedef u_int16_t WORD, *LPWORD; 159 | typedef u_int32_t DWORD, *LPDWORD; 160 | */ 161 | /* 162 | #ifndef TRUE 163 | #define FALSE (0) 164 | #define TRUE (!FALSE) 165 | #ifdef WINVER 166 | typedef int BOOL; 167 | #else 168 | typedef signed char BOOL; 169 | #endif 170 | #endif 171 | */ 172 | #define MAX_PATH 256 173 | #define _tprintf_s printf 174 | #define ARRAYSIZE(z) (sizeof(z)/sizeof((z)[0])) 175 | #define _strnicmp strncasecmp 176 | #define _tcsicmp strcasecmp 177 | #define _putts puts 178 | #define _tcsrchr strrchr 179 | #define _tcscpy_s strcpy 180 | #define _tcsncpy strncpy 181 | #define _tcslen strlen 182 | #define _tcscmp strcmp 183 | #define _stscanf sscanf 184 | 185 | #endif 186 | 187 | #endif 188 | -------------------------------------------------------------------------------- /utilities/exportvar.h: -------------------------------------------------------------------------------- 1 | #ifndef EXPORTVAR_H 2 | #define EXPORTVAR_H 3 | 4 | #include "link.h" 5 | 6 | typedef struct { 7 | FILE* stream; 8 | unsigned int pnt; 9 | unsigned int size; 10 | unsigned char *data; 11 | unsigned char *name; 12 | BOOL read; 13 | BOOL write; 14 | BOOL bin; 15 | int eof; 16 | } MFILE; 17 | 18 | MFILE *ExportVar(LPCALC, TCHAR *, symbol83P_t *); 19 | MFILE *ExportApp(LPCALC, TCHAR *, apphdr_t *); 20 | MFILE *ExportRom(TCHAR *lpszFile, LPCALC lpCalc); 21 | MFILE * ExportOS(TCHAR *lpszFile, unsigned char *buffer, int size); 22 | #ifdef _LINUX 23 | MFILE *mopen(const char *filename, const char * mode); 24 | #else 25 | MFILE *mopen(const TCHAR *filename, const TCHAR * mode); 26 | #endif 27 | int mclose(MFILE *); 28 | int meof(MFILE *); 29 | int mgetc(MFILE *); 30 | int mputc(int, MFILE *); 31 | int msize(MFILE *); 32 | 33 | #endif 34 | -------------------------------------------------------------------------------- /utilities/fileutilities.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | #include "coretypes.h" 3 | #ifdef WXVER 4 | #include 5 | extern char* wxStringToChar(wxString); 6 | #endif 7 | 8 | #include "fileutilities.h" 9 | 10 | int BrowseFile(TCHAR* lpstrFile, const TCHAR *lpstrFilter, const TCHAR *lpstrTitle, const TCHAR *lpstrDefExt, unsigned int flags) { 11 | lpstrFile[0] = '\0'; 12 | #ifdef _WINDOWS 13 | OPENFILENAME ofn; 14 | ofn.lStructSize = sizeof(OPENFILENAME); 15 | ofn.hwndOwner = GetForegroundWindow(); 16 | ofn.hInstance = NULL; 17 | ofn.lpstrFilter = (LPCTSTR) lpstrFilter; 18 | ofn.lpstrCustomFilter = NULL; 19 | ofn.nMaxCustFilter = 0; 20 | ofn.nFilterIndex = 0; 21 | ofn.lpstrFile = (LPTSTR) lpstrFile; 22 | ofn.nMaxFile = MAX_PATH; 23 | ofn.lpstrFileTitle = NULL; 24 | ofn.nMaxFileTitle = 0; 25 | ofn.lpstrInitialDir = NULL; 26 | ofn.lpstrTitle = lpstrTitle; 27 | ofn.Flags = flags | OFN_HIDEREADONLY | OFN_EXPLORER | OFN_LONGNAMES; 28 | ofn.lpstrDefExt = lpstrDefExt; 29 | ofn.lCustData = 0; 30 | ofn.lpfnHook = NULL; 31 | ofn.lpTemplateName = NULL; 32 | ofn.pvReserved = NULL; 33 | ofn.dwReserved = 0; 34 | ofn.FlagsEx = 0; 35 | if (!GetOpenFileName(&ofn)) { 36 | return 1; 37 | } 38 | #elif WXVER 39 | flags |= wxFD_OPEN | wxFD_FILE_MUST_EXIST; 40 | wxFileDialog dialog(NULL, lpstrFile, wxEmptyString, lpstrFile, lpstrFilter, flags, wxDefaultPosition, wxDefaultSize, lpstrTitle); 41 | if (dialog.ShowModal() == wxID_OK) { 42 | _tcscpy(lpstrFile, dialog.GetPath().c_str()); 43 | } else { 44 | return 1; 45 | } 46 | #endif 47 | return 0; 48 | } 49 | 50 | int SaveFile(TCHAR *lpstrFile, const TCHAR *lpstrFilter, const TCHAR *lpstrTitle, const TCHAR *lpstrDefExt, unsigned int flags, unsigned int filterIndex) { 51 | lpstrFile[0] = '\0'; 52 | #ifdef _WINDOWS 53 | OPENFILENAME ofn; 54 | ofn.lStructSize = sizeof(OPENFILENAME); 55 | ofn.hwndOwner = GetForegroundWindow(); 56 | ofn.hInstance = NULL; 57 | ofn.lpstrFilter = (LPCTSTR) lpstrFilter; 58 | ofn.lpstrCustomFilter = NULL; 59 | ofn.nMaxCustFilter = 0; 60 | ofn.nFilterIndex = filterIndex; 61 | ofn.lpstrFile = (LPTSTR) lpstrFile; 62 | ofn.nMaxFile = MAX_PATH; 63 | ofn.lpstrFileTitle = NULL; 64 | ofn.nMaxFileTitle = 0; 65 | ofn.lpstrInitialDir = NULL; 66 | ofn.lpstrTitle = lpstrTitle; 67 | ofn.Flags = flags | OFN_HIDEREADONLY | OFN_EXPLORER | OFN_LONGNAMES | OFN_OVERWRITEPROMPT; 68 | ofn.lpstrDefExt = lpstrDefExt; 69 | ofn.lCustData = 0; 70 | ofn.lpfnHook = NULL; 71 | ofn.lpTemplateName = NULL; 72 | ofn.pvReserved = NULL; 73 | ofn.dwReserved = 0; 74 | ofn.FlagsEx = 0; 75 | if (!GetSaveFileName(&ofn)) { 76 | return 1; 77 | } 78 | #elif WXVER 79 | flags |= wxFD_SAVE | wxFD_OVERWRITE_PROMPT; 80 | wxFileDialog dialog(NULL, lpstrFile, wxEmptyString, lpstrFile, lpstrFilter, flags, wxDefaultPosition, wxDefaultSize, lpstrTitle); 81 | dialog.SetFilterIndex(filterIndex); 82 | if (dialog.ShowModal() == wxID_OK) { 83 | _tcscpy(lpstrFile, dialog.GetPath().c_str()); 84 | } else { 85 | return 1; 86 | } 87 | #endif 88 | return 0; 89 | } 90 | 91 | BOOL ValidPath(TCHAR *lpstrFile) { 92 | FILE *file; 93 | #ifdef WINVER 94 | errno_t error = _tfopen_s(&file, lpstrFile, _T("r")); 95 | if (file) 96 | fclose(file); 97 | return error == 0; 98 | #else 99 | file = _tfopen_s(lpstrFile, "r"); 100 | BOOL error = file == NULL; 101 | fclose(file); 102 | return error; 103 | #endif 104 | } 105 | 106 | void GetAppDataString(TCHAR *buffer, int len) { 107 | #ifdef WINVER 108 | TCHAR *env; 109 | size_t envLen; 110 | _tdupenv_s(&env, &envLen, _T("appdata")); 111 | if (!env) { 112 | return; 113 | } 114 | StringCbCopy(buffer, len, env); 115 | StringCbCat(buffer, len, _T("\\Wabbitemu\\")); 116 | free(env); 117 | #else 118 | #ifdef _UNICODE 119 | wxString envString(getenv("appdata"), wxConvUTF8); 120 | _tcscpy(buffer, envString.c_str()); 121 | #else 122 | _tcscpy(buffer, getenv("appdata")); 123 | #endif 124 | _tcscat(buffer, _T("/wabbitemu/")); 125 | #endif 126 | } 127 | -------------------------------------------------------------------------------- /utilities/fileutilities.h: -------------------------------------------------------------------------------- 1 | #ifndef FILEUTILITIES_H 2 | #define FILEUTILITIES_H 3 | 4 | int BrowseFile(TCHAR *lpstrFile, const TCHAR *lpstrFilter, const TCHAR *lpstrTitle, const TCHAR *lpstrDefExt, unsigned int flags = 0); 5 | int SaveFile(TCHAR *lpstrFile, const TCHAR *lpstrFilter, const TCHAR *lpstrTitle, const TCHAR *lpstrDefExt, unsigned int flags = 0, unsigned int filterIndex = 0); 6 | BOOL ValidPath(TCHAR *lpstrFile); 7 | void GetAppDataString(TCHAR *buffer, int len); 8 | 9 | #endif //FILEUTILITIES_H 10 | -------------------------------------------------------------------------------- /utilities/gif.h: -------------------------------------------------------------------------------- 1 | #define USE_GIF_SIZES 2 | 3 | #define GIF_FRAME_MAX (120 * 64 * 4) 4 | #define SCRXSIZE 96 5 | #define SCRYSIZE 64 6 | 7 | #define GIF_IDLE 0 8 | #define GIF_START 1 9 | #define GIF_FRAME 2 10 | #define GIF_END 3 11 | 12 | #ifdef WINVER 13 | #include "gui.h" 14 | #else 15 | #include "coretypes.h" 16 | #endif 17 | 18 | extern int gif_write_state; 19 | extern int gif_file_size; 20 | extern TCHAR gif_file_name[256]; 21 | extern BOOL gif_autosave; 22 | extern BOOL gif_use_increasing; 23 | extern WORD gif_base_delay; 24 | extern int gif_xs; 25 | extern int gif_indiv_xs; 26 | extern int gif_ys; 27 | extern BYTE gif_frame[GIF_FRAME_MAX]; 28 | extern int gif_time; 29 | extern int gif_newframe; 30 | extern int gif_colors; 31 | extern int gif_base_delay_start; 32 | extern int gif_file_num; 33 | extern u_int gif_size; 34 | extern BOOL gif_bw; 35 | 36 | void gif_writer(int shades); 37 | -------------------------------------------------------------------------------- /utilities/gifhandle.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #include "gif.h" 4 | #ifdef WINVER // ...oops 5 | #include "resource.h" 6 | #else 7 | #include "coretypes.h" 8 | #endif 9 | #include "lcd.h" 10 | #include "gifhandle.h" 11 | #ifdef WINVER 12 | #include "fileutilities.h" 13 | #endif 14 | 15 | 16 | TCHAR *generate_gif_name(TCHAR *fn, int num, TCHAR *dest) { 17 | size_t i; 18 | for (i = _tcslen(fn) - 1; i && fn[i] != '.'; i--); 19 | 20 | if (i) { 21 | fn[i] = '\0'; 22 | } 23 | 24 | #ifdef WINVER 25 | StringCbPrintf(dest, _tcslen(dest) + 4, _T("%s%d.gif"), fn, num); 26 | #else 27 | _tprintf_s(dest, _T("%s%d.gif"), fn, num); 28 | #endif 29 | 30 | if (i) { 31 | fn[i] = '.'; 32 | } 33 | return dest; 34 | } 35 | 36 | static TCHAR gif_fn_backup[MAX_PATH]; 37 | /* 38 | * Gets where the next screenshot should be saved to. 39 | * Returns true if ready, false if user cancels 40 | */ 41 | BOOL get_gif_filename() { 42 | int i; 43 | #ifdef _WINDOWS 44 | StringCbCopy(gif_fn_backup, sizeof(gif_fn_backup), gif_file_name); 45 | #else 46 | _tcscpy_s(gif_fn_backup, gif_file_name); 47 | #endif 48 | if (gif_autosave) { 49 | /* do file save */ 50 | if (gif_use_increasing) { 51 | FILE *test = NULL; 52 | BOOL fileExists = FALSE; 53 | i = 0; 54 | 55 | do { 56 | generate_gif_name(gif_fn_backup, i, gif_file_name); 57 | #ifdef _WINDOWS 58 | _tfopen_s(&test, gif_file_name, _T("r")); 59 | #else 60 | test = _tfopen_s(gif_file_name, "r"); 61 | #endif 62 | i++; 63 | if (test) { 64 | fclose(test); 65 | fileExists = TRUE; 66 | } else { 67 | fileExists = FALSE; 68 | } 69 | } while (fileExists); 70 | } 71 | } else { 72 | #ifdef _WINDOWS 73 | #ifndef _WINDLL 74 | if (SaveFile(gif_file_name, _T("Graphics Interchange Format (*.gif)\0*.gif\0All Files (*.*)\0*.*\0\0"), 75 | _T("Wabbitemu GIF File Target"), _T("gif"))) 76 | //if we cancel, mark the menu and set to idle 77 | return FALSE; 78 | #endif 79 | #endif 80 | } 81 | return TRUE; 82 | } 83 | 84 | #ifdef HIGH_SHADE_GIF 85 | unsigned char* GIFGREYLCD(LCD_t *lpLCD) { 86 | 87 | uint8_t temp_gif[LCD_HEIGHT][LCD_WIDTH]; 88 | 89 | int level = abs((int) lpLCD->contrast - (int) lpLCD->base_level); 90 | int base = (lpLCD->contrast - 54) * 24; 91 | if (base < 0) base = 0; 92 | 93 | if (level > 12) level = 0; 94 | else level = (12 - level) * (255 - base) / lpLCD->shades / 12; 95 | 96 | u_int row, col; 97 | for (row = 0; row < LCD_HEIGHT; row++) { 98 | for (col = 0; col < LCD_MEM_WIDTH; col++) { 99 | double p0 = 0, p1 = 0, p2 = 0, p3 = 0, p4 = 0, p5 = 0, p6 = 0, p7 = 0; 100 | u_int i; 101 | 102 | for (i = 0; i < lpLCD->shades; i++) { 103 | u_int u = lpLCD->queue[i][row * 16 + col]; 104 | p7 += u & 1; u >>= 1; 105 | p6 += u & 1; u >>= 1; 106 | p5 += u & 1; u >>= 1; 107 | p4 += u & 1; u >>= 1; 108 | p3 += u & 1; u >>= 1; 109 | p2 += u & 1; u >>= 1; 110 | p1 += u & 1; u >>= 1; 111 | p0 += u; 112 | } 113 | 114 | // Convert lcd shades to gif 115 | u_char *scol = &temp_gif[row][col * 8]; 116 | scol[0] = (u_char) p0;//(p0 * level + base); 117 | scol[1] = (u_char) p1;//(p1 * level + base); 118 | scol[2] = (u_char) p2;//(p2 * level + base); 119 | scol[3] = (u_char) p3;//(p3 * level + base); 120 | scol[4] = (u_char) p4;//(p4 * level + base); 121 | scol[5] = (u_char) p5;//(p5 * level + base); 122 | scol[6] = (u_char) p6;//(p6 * level + base); 123 | scol[7] = (u_char) p7;//(p7 * level + base); 124 | } 125 | } 126 | 127 | //if (gif_size > 1) { 128 | for (row = 0; row < LCD_HEIGHT * gif_size; row++) { 129 | for (col = 0; col < LCD_WIDTH * gif_size; col++) { 130 | lpLCD->gif[row][col] = temp_gif[row / gif_size][col / gif_size]; 131 | } 132 | } 133 | //} 134 | return (uint8_t*) lpLCD->gif; 135 | } 136 | 137 | #else 138 | unsigned char* GIFGREYLCD(LCD_t *lpLCD) { 139 | unsigned int tmp; 140 | int x, y, i, bit, col; 141 | for(y = 0; y < LCD_HEIGHT * gif_size; y++) { 142 | for(x = 0; x < LCD_WIDTH * gif_size; x++) { 143 | bit = 7 - ((x / gif_size) & 0x7); 144 | col = (x / gif_size) >> 3; 145 | tmp = 0; 146 | for(i = 0; i < lpLCD->shades; i++) { 147 | if (lpLCD->queue[i]) 148 | tmp += ((lpLCD->queue[i][((y / gif_size) * LCD_MEM_WIDTH) + col] >> bit) & 0x01); 149 | } 150 | lpLCD->gif[y][x] = tmp; 151 | } 152 | } 153 | return (u_char*) lpLCD->gif; 154 | } 155 | #endif 156 | 157 | void handle_screenshot() { 158 | LCD_t* lcd; 159 | int i, j, shades = 0; 160 | BOOL running_backup[MAX_CALCS]; 161 | for (i = 0; i < MAX_CALCS; i++) { 162 | running_backup[i] = calcs[i].running; 163 | calcs[i].running = FALSE; 164 | lcd = calcs[i].cpu.pio.lcd; 165 | //find the calc with the highest number of shades and use that as our number for the gif 166 | //since I'm to lazy to implement them individually :P 167 | if (calcs[i].active && lcd && shades < lcd->shades) 168 | shades = lcd->shades; 169 | //we also need to find the size of all the LCDs 170 | } 171 | 172 | /*if ((gif_write_state != GIF_IDLE) && (!lpCalc->running)) 173 | gif_write_state = GIF_END;*/ 174 | int calc_pos = 0; 175 | //int num_calcs = calc_count(); 176 | 177 | switch (gif_write_state) { 178 | case GIF_IDLE: { 179 | gif_newframe = 0; 180 | break; 181 | } 182 | case GIF_START: { 183 | #ifdef USE_GIF_SIZES 184 | gif_xs = 0; 185 | gif_ys = 64 * gif_size; 186 | for (i = 0; i < MAX_CALCS; i++) { 187 | if (calcs[i].active) 188 | gif_xs += calcs[i].cpu.pio.lcd->width * gif_size; 189 | 190 | } 191 | #endif 192 | for (int calc_num = 0; calc_num < MAX_CALCS; calc_num++) { 193 | if (!calcs[calc_num].active) 194 | continue; 195 | lcd = calcs[calc_num].cpu.pio.lcd; 196 | #ifdef USE_GIF_SIZES 197 | gif_indiv_xs = lcd->width * gif_size; 198 | #else 199 | gif_xs = SCRXSIZE; 200 | gif_ys = SCRYSIZE; 201 | #endif 202 | gif_base_delay = gif_base_delay_start; 203 | gif_time = 0; 204 | gif_newframe = 1; 205 | gif_colors = lcd->shades + 1; 206 | 207 | GIFGREYLCD(lcd); 208 | #ifdef USE_GIF_SIZES 209 | for (i = 0; i < gif_ys; i++) 210 | for (j = 0; j < gif_indiv_xs; j++) 211 | gif_frame[i * gif_xs + j + calc_pos] = lcd->gif[i][j]; 212 | calc_pos += gif_indiv_xs; 213 | } 214 | #else 215 | for (i = 0; i < SCRYSIZE; i++) { 216 | for (j = 0; j < SCRXSIZE; j++) { 217 | gif_frame[i * gif_xs + j] = lcd->gif[i][j]; 218 | } 219 | } 220 | #endif 221 | //WriteRIFFHeader(); 222 | break; 223 | } 224 | case GIF_FRAME: 225 | { 226 | gif_time += 1; 227 | if (gif_time >= gif_base_delay) { 228 | gif_time -= gif_base_delay; 229 | gif_newframe = 1; 230 | 231 | for (int calc_num = 0; calc_num < MAX_CALCS; calc_num++) { 232 | if (!calcs[calc_num].active) 233 | continue; 234 | lcd = calcs[calc_num].cpu.pio.lcd; 235 | 236 | GIFGREYLCD(lcd); 237 | #ifdef USE_GIF_SIZES 238 | gif_indiv_xs = lcd->width * gif_size; 239 | for (i = 0; i < gif_ys; i++) 240 | for (j = 0; j < gif_indiv_xs; j++) 241 | gif_frame[i * gif_xs + j + calc_pos] = lcd->gif[i][j]; 242 | calc_pos += gif_indiv_xs; 243 | } 244 | #else 245 | for (i = 0; i < SCRYSIZE; i++) { 246 | for (j = 0; j < SCRXSIZE; j++) { 247 | gif_frame[i * gif_xs + j] = lcd->gif[i][j]; 248 | } 249 | } 250 | #endif 251 | } 252 | break; 253 | } 254 | case GIF_END: 255 | { 256 | //WriteRIFFIndex(); 257 | gif_newframe = 1; 258 | gif_file_num++; 259 | #ifdef _WINDOWS 260 | StringCbCopy(gif_file_name, sizeof(gif_file_name), gif_fn_backup); 261 | #else 262 | _tcscpy_s(gif_file_name, gif_fn_backup); 263 | #endif 264 | break; 265 | } 266 | } 267 | for (i = 0; i < MAX_CALCS; i++) 268 | calcs[i].running = running_backup[i]; 269 | 270 | if (gif_newframe) { 271 | gif_newframe = 0; 272 | gif_writer(shades); 273 | //WriteAVIFrame(); 274 | } 275 | } -------------------------------------------------------------------------------- /utilities/gifhandle.h: -------------------------------------------------------------------------------- 1 | #include "calc.h" 2 | 3 | extern int gif_base_delay_start; 4 | BOOL get_gif_filename(); 5 | void handle_screenshot(); 6 | unsigned char* GIFGREYLCD(LCD_t *lpLCD); 7 | //unsigned char* GIFBWLCD(); 8 | -------------------------------------------------------------------------------- /utilities/label.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #define LABEL_C 4 | #include "label.h" 5 | #include "core.h" 6 | #include "calc.h" 7 | 8 | #include "bcalls.h" 9 | #include "flags.h" 10 | 11 | label_struct *lookup_label(LPCALC lpCalc, TCHAR *label_name) { 12 | int i; 13 | for (i = 0; lpCalc->labels[i].name != NULL; i++) { 14 | if (_tcsicmp(lpCalc->labels[i].name, label_name) == 0) 15 | return &lpCalc->labels[i]; 16 | } 17 | return NULL; 18 | } 19 | 20 | 21 | void VoidLabels(LPCALC lpCalc) { 22 | int i; 23 | 24 | for (i = 0; lpCalc->labels[i].name != NULL; i++) { 25 | free(lpCalc->labels[i].name); 26 | lpCalc->labels[i].name = NULL; 27 | } 28 | } 29 | 30 | TCHAR* FindAddressLabel(LPCALC lpCalc, waddr_t waddr) { 31 | 32 | for (int i = 0; lpCalc->labels[i].name != NULL; i++) { 33 | label_struct *label = &lpCalc->labels[i]; 34 | if (label->IsRAM == waddr.is_ram && label->page == waddr.page && label->addr == waddr.addr) 35 | return label->name; 36 | } 37 | return NULL; 38 | } 39 | 40 | //------------------------------------------- 41 | // True means label is found and is the same 42 | // 43 | BOOL label_search_tios(TCHAR *label, int equate) { 44 | if (!label) { 45 | return FALSE; 46 | } 47 | 48 | for(int i = 0; bcalls[i].address != -1; i++ ) { 49 | if (_tcsicmp(label, bcalls[i].name) == 0) { 50 | if (bcalls[i].address == (equate & 0xFFFF) ) { 51 | return TRUE; 52 | } 53 | } 54 | } 55 | 56 | for(int i = 0; flags83p[i].flag != -1; i++ ) { 57 | if (_tcsicmp(label, flags83p[i].name) == 0) { 58 | if (flags83p[i].flag == (equate & 0xFFFF)) { 59 | return TRUE; 60 | } 61 | } 62 | for(int b = 0; b < 8; b++) { 63 | if (_tcsicmp(label, flags83p[i].bits[b].name) == 0) { 64 | if (flags83p[i].bits[b].bit == (equate & 0xFFFF)) { 65 | return TRUE; 66 | } 67 | } 68 | } 69 | } 70 | return FALSE; 71 | } 72 | 73 | 74 | int labels_app_load(LPCALC lpCalc, LPCTSTR lpszFileName) { 75 | FILE *labelFile = NULL; 76 | int i, length; 77 | #ifdef _UNICODE 78 | char readBuf[256]; 79 | #endif 80 | TCHAR buffer[256]; 81 | TCHAR name[256]; 82 | TCHAR *fileName = ((TCHAR *) lpszFileName) + _tcslen(lpszFileName); 83 | while (*--fileName != '\\'); 84 | fileName++; 85 | 86 | unsigned int equate; 87 | label_struct *label = &lpCalc->labels[0]; 88 | 89 | #ifdef _WINDOWS 90 | _tfopen_s(&labelFile, lpszFileName, _T("r")); 91 | #else 92 | labelFile = _tfopen_s(lpszFileName, "r"); 93 | #endif 94 | if (labelFile == NULL) { 95 | return 1; 96 | } 97 | 98 | // Clear out the old labels 99 | VoidLabels(lpCalc); 100 | 101 | while (!feof(labelFile)) { 102 | #ifdef _UNICODE 103 | #ifdef _WINDOWS 104 | fgets(readBuf, 256, labelFile); 105 | MultiByteToWideChar(CP_ACP, 0, readBuf, -1, buffer, ARRAYSIZE(buffer)); 106 | #else 107 | fgets(readBuf, 256, labelFile); 108 | 109 | #endif 110 | #else 111 | fgets(buffer, 256, labelFile); 112 | #endif 113 | i = 0; 114 | if (buffer[0] != ';') 115 | i = _stscanf(buffer, _T("%s = $%X"), name, &equate); 116 | if (i == 2) { 117 | length = (int) _tcslen(name); 118 | if (!label_search_tios(name, equate)) { 119 | label->name = (TCHAR *) malloc((length + 1) * sizeof(TCHAR)); 120 | #ifdef _WINDOWS 121 | StringCchCopy(label->name, length + 1, name); 122 | #else 123 | _tcscpy(label->name, name); 124 | #endif 125 | 126 | label->addr = equate & 0xFFFF; 127 | 128 | if ( (equate & 0x0000FFFF) >= 0x4000 && (equate & 0x0000FFFF) < 0x8000) { 129 | label->IsRAM = FALSE; 130 | if (lpCalc->last_transferred_app == NULL) { 131 | upages_t upage; 132 | state_userpages(&lpCalc->cpu, &upage); 133 | label->page = upage.start; 134 | } else { 135 | applist_t applist; 136 | state_build_applist(&lpCalc->cpu, &applist); 137 | for (int i = 0; i < applist.count; i++) { 138 | int len = 8; 139 | TCHAR *ptr = applist.apps[i].name + len - 1; 140 | while (isspace(*ptr--)) 141 | len--; 142 | if (!_tcsnicmp(fileName, applist.apps[i].name, len)) { 143 | label->page = applist.apps[i].page; 144 | break; 145 | } 146 | } 147 | } 148 | } else { 149 | label->IsRAM = TRUE; 150 | label->page = 1; 151 | } 152 | label++; 153 | } 154 | } 155 | } 156 | fclose(labelFile); 157 | return 0; 158 | } 159 | 160 | /* 161 | void ImportBcalls(char* fn) { 162 | int i,address; 163 | char string[256],tmp[32]; 164 | FILE* infile; 165 | 166 | infile = fopen(fn,"r"); 167 | 168 | if (!infile) { 169 | puts("COuld not open bcall file"); 170 | return; 171 | } 172 | for(address=0;address<65536;address++) { 173 | for(i=0;i<32;i++) bcalls[address][i] = 0; 174 | } 175 | while( !feof(infile) ) { 176 | fgets(string,256,infile); 177 | i = sscanf(string,"%s = $%04X",tmp,&address); 178 | if (i == 2) { 179 | _tcscpy(bcalls[address],tmp); 180 | } 181 | } 182 | fclose(infile); 183 | } 184 | */ 185 | TCHAR* FindBcall(int address) { 186 | for(int i = 0; bcalls[i].address != -1; i++ ) { 187 | if (bcalls[i].address == address) { 188 | return bcalls[i].name; 189 | } 190 | } 191 | return NULL; 192 | } 193 | 194 | 195 | void FindFlags(int flag, int bit, TCHAR **flagstring, TCHAR **bitstring) { 196 | int i,b; 197 | for(i = 0; flags83p[i].flag != -1; i++ ) { 198 | if (flags83p[i].flag == flag) { 199 | for(b = 0; b < 8; b++) { 200 | if (flags83p[i].bits[b].bit == bit) { 201 | *flagstring = flags83p[i].name; 202 | *bitstring = flags83p[i].bits[b].name; 203 | return; 204 | } 205 | } 206 | } 207 | } 208 | *flagstring = NULL; 209 | *bitstring = NULL; 210 | } 211 | 212 | 213 | 214 | 215 | 216 | 217 | -------------------------------------------------------------------------------- /utilities/label.h: -------------------------------------------------------------------------------- 1 | #ifndef _LABEL_H_TYPES 2 | #define _LABEL_H_TYPES 3 | #include "coretypes.h" 4 | 5 | typedef struct { 6 | TCHAR *name; 7 | BOOL IsRAM; 8 | uint8_t page; 9 | uint16_t addr; 10 | } label_struct; 11 | 12 | #endif 13 | 14 | #ifndef _LABEL_H_PROTOTYPES 15 | 16 | #include "calc.h" 17 | 18 | #ifdef _HAS_CALC_H 19 | #define _LABEL_H_PROTOTYPES 20 | TCHAR* FindAddressLabel(LPCALC lpCalc, waddr_t waddr); 21 | //void ImportBcalls(char* fn); 22 | TCHAR* FindBcall(int address); 23 | void FindFlags(int flag, int bit, TCHAR **flagstring, TCHAR **bitstring); 24 | 25 | void VoidLabels(LPCALC lpCalc); 26 | label_struct *lookup_label(LPCALC lpCalc, TCHAR *label); 27 | int labels_app_load(LPCALC lpCalc, LPCTSTR lpszFileName); 28 | #endif 29 | 30 | #endif 31 | 32 | -------------------------------------------------------------------------------- /utilities/print.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #include "print.h" 4 | #include "label.h" 5 | #include "core.h" 6 | 7 | 8 | #define press_text(sztext, zcolor) press_textA(sztext, zcolor, &r, hdc) 9 | 10 | static BOOL calc_size = FALSE; 11 | static size_t mspf_size = 0; 12 | static int mspf_break = 9999; 13 | 14 | void press_textA(TCHAR *szText, COLORREF zcolor, RECT *r, HDC hdc) { 15 | RECT tr; 16 | 17 | tr.left = 0; tr.right = 1; 18 | SetTextColor(hdc, zcolor); 19 | DrawText(hdc, szText, -1, &tr, DT_LEFT | DT_SINGLELINE | DT_CALCRECT); 20 | r->right = r->left + tr.right; 21 | 22 | size_t index = mspf_size; 23 | mspf_size += (int) _tcslen(szText); 24 | if (calc_size == FALSE) { 25 | const TCHAR *dot_strings[] = {_T("."), _T(".."), _T("...")}; 26 | TCHAR szNew[1024]; 27 | 28 | if (index >= mspf_break || (index < mspf_break && index+_tcslen(szText) > mspf_break)) { 29 | int break_index = (int) (max(index, mspf_break)); 30 | int break_string_index = break_index - (int) index; 31 | int str_left = (int) _tclen(&szText[break_string_index]); 32 | 33 | if (str_left > 3) 34 | str_left = 3; 35 | 36 | if (index > mspf_break) 37 | str_left -= (int) (index - mspf_break); 38 | 39 | if (str_left < 1) 40 | str_left = 1; 41 | 42 | #ifdef WINVER 43 | StringCbCopy(szNew, sizeof(szNew), szText); 44 | StringCbCopy(&szNew[break_string_index], _tcslen(dot_strings[str_left-1]) + 1, dot_strings[str_left-1]); 45 | #else 46 | strcpy(szNew, szText); 47 | strcpy(&szNew[break_string_index], dot_strings[str_left-1]); 48 | #endif 49 | 50 | szText = szNew; 51 | } 52 | 53 | DrawText(hdc, szText, -1, r, DT_LEFT | DT_SINGLELINE | DT_VCENTER); 54 | } 55 | OffsetRect(r, tr.right, 0); 56 | } 57 | 58 | 59 | void MyDrawText(LPCALC lpCalc, HDC hdc, RECT *rc, Z80_info_t* zinf, ViewType type, const TCHAR *fmt, ...) { 60 | TCHAR *p; 61 | va_list argp; 62 | RECT r = *rc; 63 | 64 | mspf_size = 0; 65 | mspf_break = 999; 66 | 67 | if (calc_size == FALSE) { 68 | calc_size = TRUE; 69 | 70 | MyDrawText(lpCalc, hdc, rc, zinf, REGULAR, fmt, zinf->a1, zinf->a2, zinf->a3, zinf->a4); 71 | 72 | TCHAR szFilltext[1024]; 73 | memset(szFilltext, 'A', mspf_size); 74 | szFilltext[mspf_size] = '\0'; 75 | 76 | RECT hr; 77 | CopyRect(&hr, rc); 78 | DrawText(hdc, szFilltext, -1, &hr, DT_LEFT | DT_SINGLELINE | DT_VCENTER | DT_CALCRECT | DT_END_ELLIPSIS | DT_MODIFYSTRING); 79 | 80 | mspf_break = (int) _tcslen(szFilltext); 81 | 82 | if (mspf_break < mspf_size) { 83 | mspf_break -= 3; 84 | } else { 85 | mspf_break++; 86 | } 87 | calc_size = FALSE; 88 | } 89 | 90 | mspf_size = 0; 91 | 92 | // Initialize arguments 93 | va_start(argp, fmt); 94 | for (p = (TCHAR *) fmt; *p && (mspf_size < mspf_break+3); p++) { 95 | if(*p != '%') { 96 | TCHAR szChar[2] = _T("x"); 97 | szChar[0] = *p; 98 | press_text(szChar, DBCOLOR_BASE); 99 | } else { 100 | switch(*++p) { 101 | case 'c': { //condition 102 | TCHAR *s = va_arg(argp, TCHAR *); 103 | press_text(s, DBCOLOR_CONDITION); 104 | break; 105 | } 106 | case 'h': { //offset 107 | int val = (int) va_arg(argp, INT_PTR); 108 | TCHAR szOffset[8]; 109 | if (val & 0x80) { 110 | _stprintf_s(szOffset, _T("%d"), val - 256); 111 | } else { 112 | _stprintf_s(szOffset, _T("+%d"), val); 113 | } 114 | 115 | press_text(szOffset, RGB(0, 0, 0)); 116 | break; 117 | } 118 | case 'd': { //number 119 | int val = (int) va_arg(argp, INT_PTR); 120 | TCHAR szAddr[16]; 121 | _stprintf_s(szAddr, _T("%d"), val); 122 | 123 | press_text(szAddr, RGB(0, 0, 0)); 124 | break; 125 | } 126 | case 'l': 127 | { 128 | TCHAR *s = va_arg(argp, TCHAR *); 129 | press_text(s, RGB(0, 0, 0)); 130 | break; 131 | } 132 | case 's': 133 | { 134 | TCHAR *s = va_arg(argp, TCHAR *); 135 | press_text(s, DBCOLOR_BASE); 136 | break; 137 | } 138 | case 'g': 139 | { 140 | waddr_t waddr = OffsetWaddr(lpCalc->cpu.mem_c, REGULAR, zinf->waddr, 2 + ((char) va_arg(argp, INT_PTR))); 141 | TCHAR *name; 142 | 143 | name = FindAddressLabel(lpCalc, waddr); 144 | 145 | if (name) { 146 | press_text(name, RGB(0, 0, 0)); 147 | } else { 148 | TCHAR szAddr[16]; 149 | _stprintf_s(szAddr, _T("$%04X"), waddr.addr); 150 | press_text(szAddr, RGB(0, 0, 0)); 151 | } 152 | break; 153 | } 154 | case 'a': //address 155 | { 156 | waddr_t waddr = OffsetWaddr(lpCalc->cpu.mem_c, REGULAR, zinf->waddr, 2); 157 | TCHAR *name; 158 | int val = (int) va_arg(argp, INT_PTR); 159 | 160 | name = FindAddressLabel(lpCalc, addr_to_waddr(lpCalc->cpu.mem_c, val)); 161 | 162 | if (name) { 163 | press_text(name, RGB(0, 0, 0)); 164 | } else { 165 | TCHAR szAddr[16]; 166 | _stprintf_s(szAddr, _T("$%04X"), val); 167 | press_text(szAddr, RGB(0, 0, 0)); 168 | } 169 | break; 170 | } 171 | case 'r': 172 | { 173 | TCHAR *szReg = va_arg(argp, TCHAR *); 174 | if (!_tcscmp(szReg, _T("(hl)"))) { 175 | press_text(_T("("), DBCOLOR_BASE); 176 | press_text(_T("hl"), DBCOLOR_HILIGHT); 177 | press_text(_T(")"), DBCOLOR_BASE); 178 | } else 179 | press_text(szReg, DBCOLOR_HILIGHT); 180 | break; 181 | } 182 | case 'x': 183 | { 184 | int val = (int) va_arg(argp, INT_PTR); 185 | TCHAR szAddr[16]; 186 | StringCbPrintf(szAddr, sizeof(szAddr), _T("$%02X"), val); 187 | press_text(szAddr, RGB(0, 0, 0)); 188 | break; 189 | } 190 | } 191 | } 192 | } 193 | va_end(argp); 194 | } 195 | 196 | TCHAR* mysprintf(LPCALC lpCalc, Z80_info_t* zinf, ViewType type, const TCHAR *fmt, ...) { 197 | TCHAR *p; 198 | static TCHAR end_buf[1024] = _T("\0"); 199 | va_list argp; 200 | 201 | mspf_size = 0; 202 | mspf_break = 999; 203 | 204 | mspf_size = 0; 205 | 206 | // Initialize arguments 207 | va_start(argp, fmt); 208 | for (p = (TCHAR *) fmt; *p && (mspf_size < mspf_break+3); p++) { 209 | if(*p != '%') { 210 | TCHAR szChar[2] = _T("x"); 211 | szChar[0] = *p; 212 | StringCbCat(end_buf, sizeof(end_buf), szChar); 213 | } else { 214 | switch(*++p) { 215 | case 'c': {//condition 216 | TCHAR *s = va_arg(argp, TCHAR *); 217 | StringCbCat(end_buf, sizeof(end_buf), s); 218 | break; 219 | } 220 | case 'h': {//offset 221 | int val = (int) va_arg(argp, INT_PTR); 222 | TCHAR szOffset[8]; 223 | #ifdef WINVER 224 | _stprintf_s(szOffset, _T("%+d"),val); 225 | #else 226 | sprintf(szOffset, "%+d",val); 227 | #endif 228 | StringCbCat(end_buf, sizeof(end_buf), szOffset); 229 | break; 230 | } 231 | case 'd': //number 232 | { 233 | int val = (int) va_arg(argp, INT_PTR); 234 | TCHAR szAddr[16]; 235 | #ifdef WINVER 236 | _stprintf_s(szAddr, _T("%d"), val); 237 | #else 238 | sprintf(szAddr, "%d",val); 239 | #endif 240 | StringCbCat(end_buf, sizeof(end_buf), szAddr); 241 | break; 242 | } 243 | case 'l': 244 | { 245 | TCHAR *s = va_arg(argp, TCHAR *); 246 | StringCbCat(end_buf, sizeof(end_buf), s); 247 | break; 248 | } 249 | case 's': 250 | { 251 | TCHAR *s = va_arg(argp, TCHAR *); 252 | StringCbCat(end_buf, sizeof(end_buf), s); 253 | break; 254 | } 255 | case 'g': 256 | { 257 | waddr_t waddr = OffsetWaddr(lpCalc->cpu.mem_c, type, zinf->waddr, 2 + (char) va_arg(argp, INT_PTR)); 258 | TCHAR *name; 259 | 260 | name = FindAddressLabel(lpCalc, waddr); 261 | 262 | if (name) { 263 | StringCbCat(end_buf, sizeof(end_buf), name); 264 | } else { 265 | TCHAR szAddr[16]; 266 | StringCbPrintf(szAddr, sizeof(szAddr), _T("$%04X"), waddr.addr); 267 | StringCbCat(end_buf, sizeof(end_buf), szAddr); 268 | } 269 | break; 270 | } 271 | case 'a': //address 272 | { 273 | unsigned short addr = zinf->waddr.addr + 2; 274 | TCHAR *name; 275 | int val; 276 | val = (int) va_arg(argp, INT_PTR); 277 | 278 | name = FindAddressLabel(lpCalc, addr_to_waddr(lpCalc->cpu.mem_c, val)); 279 | 280 | if (name) { 281 | StringCbCat(end_buf, sizeof(end_buf), name); 282 | } else { 283 | TCHAR szAddr[16]; 284 | StringCbPrintf(szAddr, sizeof(szAddr), _T("$%04X"), val); 285 | StringCbCat(end_buf, sizeof(end_buf), szAddr); 286 | } 287 | break; 288 | } 289 | case 'r': 290 | { 291 | TCHAR *szReg = va_arg(argp, TCHAR *); 292 | if (!_tcscmp(szReg, _T("(hl)"))) { 293 | StringCbCat(end_buf, sizeof(end_buf), _T("(hl)")); 294 | } else 295 | StringCbCat(end_buf, sizeof(end_buf), szReg); 296 | break; 297 | } 298 | case 'x': 299 | { 300 | int val = (int) va_arg(argp, INT_PTR); 301 | TCHAR szAddr[16]; 302 | #ifdef WINVER 303 | StringCbPrintf(szAddr, sizeof(szAddr), _T("$%02X"), val); 304 | #else 305 | sprintf(szAddr, "$%02X", val); 306 | #endif 307 | StringCbCat(end_buf, sizeof(end_buf), szAddr); 308 | break; 309 | } 310 | } 311 | } 312 | } 313 | va_end(argp); 314 | return end_buf; 315 | } -------------------------------------------------------------------------------- /utilities/print.h: -------------------------------------------------------------------------------- 1 | #ifndef PRINT_H 2 | #define PRINT_H 3 | 4 | #include "disassemble.h" 5 | #include "calc.h" 6 | #include "dbcommon.h" 7 | 8 | void MyDrawText(LPCALC, HDC, RECT *, Z80_info_t *, ViewType, const TCHAR *, ...); 9 | TCHAR* mysprintf(LPCALC, Z80_info_t *, ViewType, const TCHAR *, ...); 10 | 11 | #define DBCOLOR_BASE (RGB(4, 72, 117)) 12 | //#define DBCOLOR_HILIGHT (RGB(112, 169, 168)) 13 | #define DBCOLOR_HILIGHT (RGB(108, 173, 101)) 14 | #define DBCOLOR_CONDITION (RGB(40, 160, 180)) 15 | 16 | #endif 17 | -------------------------------------------------------------------------------- /utilities/savestate.h: -------------------------------------------------------------------------------- 1 | #ifndef SAVESTATE_H 2 | #define SAVESTATE_H 3 | 4 | #include "lcd.h" 5 | 6 | typedef struct { 7 | char tag[4]; 8 | int pnt; 9 | int size; 10 | unsigned char *data; 11 | } CHUNK_t; 12 | 13 | 14 | typedef struct { 15 | int version_major; 16 | int version_minor; 17 | int version_build; 18 | int model; 19 | int chunk_count; 20 | TCHAR author[32]; 21 | TCHAR comment[64]; 22 | CHUNK_t* chunks[512]; 23 | } SAVESTATE_t; 24 | 25 | 26 | #define CUR_MAJOR 0 27 | #define CUR_MINOR 1 28 | #define CUR_BUILD 1 29 | 30 | 31 | #define DETECT_STR "*WABBIT*" 32 | #define DETECT_CMP_STR "*WABCMP*" 33 | #define FLASH_HEADER "**TIFL**" 34 | 35 | #define NO_CMP 0 36 | #define ZLIB_CMP 1 37 | 38 | #define SAVE_HEADERSIZE 116 39 | 40 | #define INFO_tag "INFO" 41 | #define CPU_tag "CPU " 42 | #define MEM_tag "MEMC" 43 | #define ROM_tag "ROM " 44 | #define RAM_tag "RAM " 45 | #define TIMER_tag "TIME" 46 | #define LCD_tag "LCD " 47 | #define LINK_tag "LINK" 48 | #define STDINT_tag "STDI" 49 | #define SE_AUX_tag "SEAX" 50 | #define USB_tag "USB " 51 | #define REMAP_tag "RMAP" 52 | #define RAM_LIMIT_tag "RMLM" 53 | #define RAM_BREAKS_tag "RBRK" 54 | #define FLASH_BREAKS_tag "FBRK" 55 | #define NUM_FLASH_BREAKS_tag "NFBK" 56 | #define NUM_RAM_BREAKS_tag "NRBK" 57 | 58 | void WriteSave(const TCHAR *, SAVESTATE_t *, int); 59 | void LoadSlot(SAVESTATE_t* , void *lpInput); 60 | SAVESTATE_t* SaveSlot(void *lpInput); 61 | SAVESTATE_t* CreateSave(const TCHAR *, const TCHAR *, int); 62 | SAVESTATE_t* ReadSave(FILE *ifile); 63 | void FreeSave(SAVESTATE_t *); 64 | char* GetRomOnly(SAVESTATE_t *save, int *); 65 | void LoadLCD(SAVESTATE_t *, LCD_t *); 66 | 67 | #endif 68 | 69 | -------------------------------------------------------------------------------- /utilities/sendfile.c: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | 3 | #include "calc.h" 4 | #include "link.h" 5 | #include "label.h" 6 | 7 | //Sends a file to the given calculator 8 | //from the given filename 9 | LINK_ERR SendFile(const LPCALC lpCalc, LPCTSTR lpszFileName, SEND_FLAG Destination) 10 | { 11 | TIFILE_t *var = newimportvar(lpszFileName, FALSE); 12 | 13 | LINK_ERR result; 14 | if (var != NULL) 15 | { 16 | switch(var->type) 17 | { 18 | case GROUP_TYPE: 19 | case VAR_TYPE: 20 | case FLASH_TYPE: 21 | { 22 | if (var->type == FLASH_TYPE) 23 | lpCalc->running = FALSE; 24 | lpCalc->cpu.pio.link->vlink_size = var->length; 25 | lpCalc->cpu.pio.link->vlink_send = 0; 26 | 27 | result = link_send_var(&lpCalc->cpu, var, (SEND_FLAG) Destination); 28 | if (var->type == FLASH_TYPE) 29 | { 30 | // Rebuild the applist 31 | state_build_applist(&lpCalc->cpu, &lpCalc->applist); 32 | 33 | u_int i; 34 | for (i = 0; i < lpCalc->applist.count; i++) { 35 | if (_tcsncmp((TCHAR *) var->flash->name, lpCalc->applist.apps[i].name, 8) == 0) { 36 | lpCalc->last_transferred_app = &lpCalc->applist.apps[i]; 37 | break; 38 | } 39 | } 40 | if (var->flash->type == FLASH_TYPE_OS) { 41 | calc_reset(lpCalc); 42 | //calc_turn_on(lpCalc); 43 | } 44 | lpCalc->running = TRUE; 45 | } 46 | break; 47 | } 48 | case BACKUP_TYPE: 49 | lpCalc->cpu.pio.link->vlink_size = var->length; 50 | lpCalc->cpu.pio.link->vlink_send = 0; 51 | result = link_send_backup(&lpCalc->cpu, var, (SEND_FLAG) Destination); 52 | break; 53 | case ROM_TYPE: 54 | case SAV_TYPE: 55 | { 56 | FreeTiFile(var); 57 | var = NULL; 58 | if (rom_load(lpCalc, lpszFileName) == TRUE) { 59 | result = LERR_SUCCESS; 60 | } else { 61 | result = LERR_LINK; 62 | } 63 | break; 64 | } 65 | case LABEL_TYPE: 66 | { 67 | _tcscpy_s(lpCalc->labelfn, lpszFileName); 68 | VoidLabels(lpCalc); 69 | labels_app_load(lpCalc, lpCalc->labelfn); 70 | result = LERR_SUCCESS; 71 | break; 72 | } 73 | case BREAKPOINT_TYPE: 74 | break; 75 | } 76 | if (var) 77 | { 78 | FreeTiFile(var); 79 | } 80 | 81 | return result; 82 | } 83 | else 84 | { 85 | return LERR_FILE; 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /utilities/sendfile.h: -------------------------------------------------------------------------------- 1 | #ifndef _SENDFILE_H 2 | #define _SENDFILE_H 3 | 4 | #include "link.h" 5 | 6 | LINK_ERR SendFile(const LPCALC lpCalc, LPCTSTR lpszFileName, SEND_FLAG Destination); 7 | 8 | #endif -------------------------------------------------------------------------------- /utilities/sound.h: -------------------------------------------------------------------------------- 1 | #ifndef SOUND_H 2 | #define SOUND_H 3 | 4 | #include "core.h" 5 | 6 | #define SampleRate (48000) 7 | #define Channels (2) 8 | #define SampleSize (1) 9 | #define PreferedSamples (4096) 10 | #define BufferBanks (4) 11 | 12 | 13 | #define BankTime (((float)PreferedSamples)/((float)SampleRate)) 14 | #define SampleLength ((1.0f)/((float)SampleRate)) 15 | #define SampleSizeBits (SampleSize<<3) 16 | #define BankSize (PreferedSamples*Channels*SampleSize) 17 | 18 | #define BufferSamples (SampleRate) 19 | #define AudioBufferSize (BufferSamples*Channels*SampleSize) 20 | 21 | 22 | typedef struct SAMPLE SAMPLE_t; 23 | 24 | #pragma pack(1) 25 | struct SAMPLE { 26 | unsigned char left; 27 | unsigned char right; 28 | }; 29 | 30 | #pragma pack() 31 | 32 | 33 | typedef struct { 34 | int init; 35 | int enabled; 36 | volatile int endsnd; 37 | HWAVEOUT hWaveOut; 38 | WAVEFORMATEX wfx; 39 | 40 | WAVEHDR waveheader[BufferBanks]; 41 | SAMPLE_t playbuf[BufferBanks][PreferedSamples]; 42 | 43 | 44 | SAMPLE_t buffer[BufferSamples]; 45 | 46 | int CurPnt; 47 | int PlayPnt; 48 | 49 | double PlayTime; 50 | double LastSample; 51 | 52 | int LeftOn; 53 | double LastFlipLeft; 54 | double HighLengLeft; 55 | 56 | int RightOn; 57 | double LastFlipRight; 58 | double HighLengRight; 59 | 60 | double volume; 61 | timerc *timer_c; 62 | 63 | } AUDIO_t; 64 | 65 | 66 | int soundinit(void *); 67 | int playsound(AUDIO_t *); 68 | int pausesound(AUDIO_t *); 69 | void togglesound(AUDIO_t *); 70 | int FlippedLeft(CPU_t *, int ); 71 | int FlippedRight(CPU_t *, int ); 72 | int nextsample(CPU_t *); 73 | void KillSound(AUDIO_t *); 74 | 75 | #endif 76 | -------------------------------------------------------------------------------- /utilities/types.h: -------------------------------------------------------------------------------- 1 | #ifndef TYPES_H 2 | #define TYPES_H 3 | 4 | #ifdef WINVER 5 | #include 6 | typedef BYTE uint8_t; 7 | typedef WORD uint16_t; 8 | typedef DWORD uint32_t; 9 | #else 10 | typedef unsigned char uint8_t; 11 | typedef unsigned short uint16_t; 12 | typedef unsigned int uint32_t; 13 | typedef uint16_t WORD; 14 | typedef uint32_t DWORD; 15 | typedef uint8_t BYTE; 16 | #endif 17 | 18 | #endif 19 | -------------------------------------------------------------------------------- /utilities/var.h: -------------------------------------------------------------------------------- 1 | #ifndef VAR_H 2 | #define VAR_H 3 | 4 | #include "stdafx.h" 5 | #include "savestate.h" 6 | 7 | typedef struct INTELHEX { 8 | int DataSize; 9 | int Address; 10 | int Type; 11 | BYTE Data[256]; 12 | int CheckSum; 13 | } INTELHEX_t; 14 | 15 | #pragma pack(1) 16 | 17 | typedef struct TIFLASH { 18 | unsigned char sig[8]; 19 | unsigned char rev[2]; 20 | unsigned char flag; 21 | unsigned char object; 22 | unsigned char date[4]; 23 | unsigned char namelength; 24 | unsigned char name[8]; 25 | unsigned char filler[23]; 26 | unsigned char device; 27 | unsigned char type; 28 | unsigned char filler2[24]; 29 | unsigned int hexsize; 30 | // int rpage[256]; 31 | int pagesize[256]; 32 | unsigned char *data[256]; 33 | // unsigned short chksum; 34 | 35 | unsigned int pages; //total number of pages. 36 | 37 | } TIFLASH_t; 38 | 39 | 40 | 41 | typedef struct ROM { 42 | int size; 43 | char version[32]; 44 | unsigned char *data; 45 | } ROM_t; 46 | 47 | typedef struct TIBACKUP { 48 | unsigned short headersize; // size of the header up to name, sometimes ignored 49 | unsigned short length1; // data size 50 | unsigned char vartype; // what type of varible 51 | unsigned short length2; // data size 52 | unsigned short length3; // data size 53 | unsigned short address; // duplicate of data size 54 | 55 | unsigned short length1a; // Repeats of the data length. 56 | unsigned char *data1; // pointer to data 57 | 58 | unsigned short length2a; // data size 59 | unsigned char *data2; // pointer to data 60 | 61 | unsigned short length3a; // data size 62 | unsigned char *data3; // pointer to data 63 | 64 | 65 | } TIBACKUP_t; 66 | 67 | typedef struct TIVAR { 68 | unsigned short headersize; // size of the header up to name, sometimes ignored 69 | unsigned short length; // data size 70 | unsigned char vartype; // what type of variable 71 | unsigned char name_length; // 85/86 only name length is variable 72 | unsigned char name[8]; // null padded name 73 | unsigned char version; // 0 83+only 74 | unsigned char flag; // bit 7 is if flash 83+only 75 | unsigned short length2; // duplicate of data size 76 | unsigned char *data; // pointer to data 77 | } TIVAR_t; 78 | 79 | typedef struct TIFILE { 80 | unsigned char sig[8]; 81 | unsigned char subsig[3]; 82 | unsigned char comment[42]; 83 | unsigned char length; 84 | TIVAR_t *var; 85 | TIVAR_t *vars[256]; 86 | unsigned char chksum; 87 | int model; 88 | int type; 89 | ROM_t *rom; 90 | TIFLASH_t *flash; 91 | SAVESTATE_t *save; 92 | TIBACKUP_t *backup; 93 | } TIFILE_t; 94 | 95 | 96 | #pragma pack() 97 | 98 | #define TI_FLASH_HEADER_SIZE 8+2+1+1+4+1+8+23+1+1+24+4 99 | #define TI_FILE_HEADER_SIZE 8+3+42/*+2*/ 100 | #define TI_VAR_HEADER_SIZE 2+2+1+8 101 | 102 | 103 | #define ROM_TYPE 1 //Rom 104 | #define FLASH_TYPE 2 //Flash application or OS 105 | #define VAR_TYPE 3 //most varibles can be supported under an umbrella type 106 | #define SAV_TYPE 4 //Wabbit specific saves. 107 | #define BACKUP_TYPE 5 //Wabbit specific saves. 108 | #define LABEL_TYPE 6 //Lab file 109 | #define BREAKPOINT_TYPE 7 //breakpoint file 110 | #define GROUP_TYPE 8 //groups are stored weirdly so they get a weird type 111 | #define ZIP_TYPE 9 //zip/tig file 112 | 113 | #define FLASH_TYPE_OS 0x23 114 | #define FLASH_TYPE_APP 0x24 115 | 116 | int FindRomVersion(int, char*, unsigned char*, int); 117 | int ReadIntelHex(FILE *ifile, INTELHEX_t *ihex); 118 | TIFILE_t* newimportvar(LPCTSTR FilePath, BOOL only_check_header = FALSE); 119 | TIFILE_t* FreeTiFile(TIFILE_t *); 120 | 121 | #endif 122 | -------------------------------------------------------------------------------- /utilities/zlibcmp.c: -------------------------------------------------------------------------------- 1 | /* zpipe.c: example of proper use of zlib's inflate() and deflate() 2 | Not copyrighted -- provided to the public domain 3 | Version 1.4 11 December 2005 Mark Adler */ 4 | 5 | /* Version history: 6 | 1.0 30 Oct 2004 First version 7 | 1.1 8 Nov 2004 Add void casting for unused return values 8 | Use switch statement for inflate() return values 9 | 1.2 9 Nov 2004 Add assertions to document zlib guarantees 10 | 1.3 6 Apr 2005 Remove incorrect assertion in inf() 11 | 1.4 11 Dec 2005 Add hack to avoid MSDOS end-of-line conversions 12 | Avoid some compiler warnings for input and output buffers 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | #include "zlib.h" 19 | 20 | #define CHUNK 16384 21 | 22 | /* Compress from file source to file dest until EOF on source. 23 | def() returns Z_OK on success, Z_MEM_ERROR if memory could not be 24 | allocated for processing, Z_STREAM_ERROR if an invalid compression 25 | level is supplied, Z_VERSION_ERROR if the version of zlib.h and the 26 | version of the library linked do not match, or Z_ERRNO if there is 27 | an error reading or writing the files. */ 28 | int def(FILE *source, FILE *dest, int level) 29 | { 30 | int ret, flush; 31 | unsigned have; 32 | z_stream strm; 33 | unsigned char in[CHUNK]; 34 | unsigned char out[CHUNK]; 35 | 36 | /* allocate deflate state */ 37 | strm.zalloc = Z_NULL; 38 | strm.zfree = Z_NULL; 39 | strm.opaque = Z_NULL; 40 | ret = deflateInit(&strm, level); 41 | if (ret != Z_OK) 42 | return ret; 43 | 44 | /* compress until end of file */ 45 | do { 46 | strm.avail_in = fread(in, 1, CHUNK, source); 47 | if (ferror(source)) { 48 | (void)deflateEnd(&strm); 49 | return Z_ERRNO; 50 | } 51 | flush = feof(source) ? Z_FINISH : Z_NO_FLUSH; 52 | strm.next_in = in; 53 | 54 | /* run deflate() on input until output buffer not full, finish 55 | compression if all of source has been read in */ 56 | do { 57 | strm.avail_out = CHUNK; 58 | strm.next_out = out; 59 | ret = deflate(&strm, flush); /* no bad return value */ 60 | assert(ret != Z_STREAM_ERROR); /* state not clobbered */ 61 | have = CHUNK - strm.avail_out; 62 | if (fwrite(out, 1, have, dest) != have || ferror(dest)) { 63 | (void)deflateEnd(&strm); 64 | return Z_ERRNO; 65 | } 66 | } while (strm.avail_out == 0); 67 | assert(strm.avail_in == 0); /* all input will be used */ 68 | 69 | /* done when last data in file processed */ 70 | } while (flush != Z_FINISH); 71 | assert(ret == Z_STREAM_END); /* stream will be complete */ 72 | 73 | /* clean up and return */ 74 | (void)deflateEnd(&strm); 75 | return Z_OK; 76 | } 77 | 78 | /* Decompress from file source to file dest until stream ends or EOF. 79 | inf() returns Z_OK on success, Z_MEM_ERROR if memory could not be 80 | allocated for processing, Z_DATA_ERROR if the deflate data is 81 | invalid or incomplete, Z_VERSION_ERROR if the version of zlib.h and 82 | the version of the library linked do not match, or Z_ERRNO if there 83 | is an error reading or writing the files. */ 84 | int inf(FILE *source, FILE *dest) 85 | { 86 | int ret; 87 | unsigned have; 88 | z_stream strm; 89 | unsigned char in[CHUNK]; 90 | unsigned char out[CHUNK]; 91 | 92 | /* allocate inflate state */ 93 | strm.zalloc = Z_NULL; 94 | strm.zfree = Z_NULL; 95 | strm.opaque = Z_NULL; 96 | strm.avail_in = 0; 97 | strm.next_in = Z_NULL; 98 | ret = inflateInit(&strm); 99 | if (ret != Z_OK) 100 | return ret; 101 | 102 | /* decompress until deflate stream ends or end of file */ 103 | do { 104 | strm.avail_in = fread(in, 1, CHUNK, source); 105 | if (ferror(source)) { 106 | (void)inflateEnd(&strm); 107 | return Z_ERRNO; 108 | } 109 | if (strm.avail_in == 0) 110 | break; 111 | strm.next_in = in; 112 | 113 | /* run inflate() on input until output buffer not full */ 114 | do { 115 | strm.avail_out = CHUNK; 116 | strm.next_out = out; 117 | ret = inflate(&strm, Z_NO_FLUSH); 118 | assert(ret != Z_STREAM_ERROR); /* state not clobbered */ 119 | switch (ret) { 120 | case Z_NEED_DICT: 121 | ret = Z_DATA_ERROR; /* and fall through */ 122 | case Z_DATA_ERROR: 123 | case Z_MEM_ERROR: 124 | (void)inflateEnd(&strm); 125 | return ret; 126 | } 127 | have = CHUNK - strm.avail_out; 128 | if (fwrite(out, 1, have, dest) != have || ferror(dest)) { 129 | (void)inflateEnd(&strm); 130 | return Z_ERRNO; 131 | } 132 | } while (strm.avail_out == 0); 133 | 134 | /* done when inflate() says it's done */ 135 | } while (ret != Z_STREAM_END); 136 | 137 | /* clean up and return */ 138 | (void)inflateEnd(&strm); 139 | return ret == Z_STREAM_END ? Z_OK : Z_DATA_ERROR; 140 | } 141 | 142 | /* report a zlib or i/o error */ 143 | void zerr(int ret) 144 | { 145 | fputs("zpipe: ", stderr); 146 | switch (ret) { 147 | case Z_ERRNO: 148 | if (ferror(stdin)) 149 | fputs("error reading stdin\n", stderr); 150 | if (ferror(stdout)) 151 | fputs("error writing stdout\n", stderr); 152 | break; 153 | case Z_STREAM_ERROR: 154 | fputs("invalid compression level\n", stderr); 155 | break; 156 | case Z_DATA_ERROR: 157 | fputs("invalid or incomplete deflate data\n", stderr); 158 | break; 159 | case Z_MEM_ERROR: 160 | fputs("out of memory\n", stderr); 161 | break; 162 | case Z_VERSION_ERROR: 163 | fputs("zlib version mismatch!\n", stderr); 164 | } 165 | } 166 | 167 | 168 | 169 | -------------------------------------------------------------------------------- /utilities/zlibcmp.h: -------------------------------------------------------------------------------- 1 | #ifndef ZLIBCMP_H 2 | #define ZLIBCMP_H 3 | 4 | int def(FILE *source, FILE *dest, int level); 5 | int inf(FILE *source, FILE *dest); 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /z.rom: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/alberthdev/wxwabbitemu/7b9ef9d3109355c053d83ae6be67cd75dd6ca8dc/z.rom --------------------------------------------------------------------------------